⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 thresher.cpp

📁 完整的基于Conxant平台的USB电视棒的WIN驱动程序。
💻 CPP
📖 第 1 页 / 共 3 页
字号:

    if(video_mode == VIDEO_MODE_NTSC)
    {
        initializeRegisters_NTSC();
    }
    else if(video_mode == VIDEO_MODE_SECAM)
    {
        initializeRegisters_SECAM();
    }
    else if(video_mode == VIDEO_MODE_PAL_N)
    {
        initializeRegisters_PAL_N();
    }
    else if(video_mode == VIDEO_MODE_PAL_NC)
    {
        initializeRegisters_PAL_NC();
    }
    else
    {
        initializeRegisters_PAL();
    }

    // Handle any MODE_CTRL overrides
    do_MODE_CTRL_overrides();
}

/////////////////////////////////////////////////////////////////////////////////////////
VOID Thresher::setResolution(ULONG width, ULONG height)
{
    _width = width;
    _height = height;

    // Note: This function appears to set only the width.  The
    // height is set when it is put into PAL or NTSC mode.

    // This is calculated as: (720/width - 1)*2^20
    // or ((720 - width)*2^20)/width  (doesn't require floating point)
    const DWORD MAX_WIDTH = 720;

    // validate the width - cannot be negative
    if (width > MAX_WIDTH)
    {
        DbgLogWarn(("Thresher::setResolution : width %d > MAX_WIDTH %d ! resetting to MAX_WIDTH \n", width, MAX_WIDTH));
        _width = width = MAX_WIDTH;
    }

    DWORD hscale = ((MAX_WIDTH-width)*(0x00100000))/width;
    hscale &= 0x00FFFFFF;
    _p_registers->writeDword(HSCALE_CTRL, hscale);

    // Vertical scaling = 2^16 - (scaling ratio - 1)*2^9
    // This is calculated as 2^16 - (max_height/height - 1)*2^9
    // or 2^16 - ((max_height - height)*2^9)/height  (doesn't require floating point)

    DWORD MAX_HEIGHT = 480;

    if (_video_mode == VIDEO_MODE_NTSC)
        MAX_HEIGHT = 480;
    else
        MAX_HEIGHT = 576;

    // validate the height - cannot be negative
    if (height > MAX_HEIGHT)
    {
        DbgLogWarn(("Thresher::setResolution : height %d > MAX_HEIGHT %d ! resetting to MAX_HEIGHT \n", height, MAX_HEIGHT));
        _height = height = MAX_HEIGHT;
    }

    DWORD vscale = 0x00010000 - ((MAX_HEIGHT-height)*0x00000200)/height;
    vscale &= 0x00001FFF;

    _p_registers->writeDword(VSCALE_CTRL, vscale);

    DbgLogInfo(("Thresher::setResolution : hscale = 0x%x, vscale = 0x%x\n", hscale, vscale));
}

/////////////////////////////////////////////////////////////////////////////////////////
VOID Thresher::waitForLock()
{
    //not used, same as corona
}

/////////////////////////////////////////////////////////////////////////////////////////
BOOLEAN Thresher::setBrightness(INT brightness)
{
    if((brightness > VIDEO_PROCAMP_MAX) || (brightness < VIDEO_PROCAMP_MIN))
    {
        return FALSE;
    }

    _brightness = brightness;

    INT new_brightness = 0;
    map(
        VIDEO_PROCAMP_MIN,
        VIDEO_PROCAMP_MAX,
        brightness,
        SIGNED_BYTE_MIN,
        SIGNED_BYTE_MAX,
        &new_brightness);

    _preserved_brightness = static_cast<BYTE>(new_brightness);
    if(!_video_muted)
    {
        _p_registers->writeByte(BRIGHTNESS_CTRL_BYTE, _preserved_brightness);
    }

    return TRUE;
}


/////////////////////////////////////////////////////////////////////////////////////////
BOOLEAN Thresher::setContrast(INT contrast)
{
    if((contrast > VIDEO_PROCAMP_MAX) || (contrast < VIDEO_PROCAMP_MIN))
    {
        return FALSE;
    }

    _contrast = contrast;

    INT new_contrast = 0;
    map(
        VIDEO_PROCAMP_MIN,
        VIDEO_PROCAMP_MAX,
        contrast,
        UNSIGNED_BYTE_MIN,
        UNSIGNED_BYTE_MAX,
        &new_contrast);

    _preserved_contrast = static_cast<BYTE>(new_contrast);
    if(!_video_muted)
    {
        _p_registers->writeByte(CONTRAST_CTRL_BYTE, _preserved_contrast);
    }

    return TRUE;
}

/////////////////////////////////////////////////////////////////////////////////////////
BOOLEAN Thresher::setHue(INT hue)
{
    if((hue > VIDEO_PROCAMP_MAX) || (hue < VIDEO_PROCAMP_MIN))
    {
        return FALSE;
    }

    _hue = hue;

    INT new_hue = 0;
    map(
        VIDEO_PROCAMP_MIN,
        VIDEO_PROCAMP_MAX,
        hue,
        SIGNED_BYTE_MIN,
        SIGNED_BYTE_MAX,
        &new_hue);

    _p_registers->writeByte(HUE_CTRL_BYTE, (BYTE) new_hue);

    return TRUE;
}


/////////////////////////////////////////////////////////////////////////////////////////
BOOLEAN Thresher::setSaturation(INT saturation)
{
    if((saturation > VIDEO_PROCAMP_MAX) || (saturation < VIDEO_PROCAMP_MIN))
    {
        return FALSE;
    }

    _saturation = saturation;

    INT new_saturation = 0;
    map(
        VIDEO_PROCAMP_MIN,
        VIDEO_PROCAMP_MAX,
        saturation,
        UNSIGNED_BYTE_MIN,
        UNSIGNED_BYTE_MAX,
        &new_saturation);

    _preserved_saturation = static_cast<BYTE>(new_saturation);
    if(!_video_muted)
    {
        _p_registers->writeByte(USAT_CTRL_BYTE, _preserved_saturation);
        _p_registers->writeByte(VSAT_CTRL_BYTE, _preserved_saturation);
    }

    return TRUE;
}


/////////////////////////////////////////////////////////////////////////////////////////
BOOLEAN Thresher::setSharpness(INT sharpness)
{
    if((sharpness > VIDEO_PROCAMP_MAX) || (sharpness < VIDEO_PROCAMP_MIN))
    {
        return FALSE;
    }

    _sharpness = sharpness;

    INT new_sharpness = 0;
    map(
        0,
        100,
        sharpness,
        0,
        4,
        &new_sharpness);

    //These are in order from least sharp to most sharp
    BYTE sharpness_mappings[5] =
    {
        0x00,   // sharpness enhancement (aka luma peaking) disabled
        0x04,   // +2.0dB response @ center freq
        0x05,   // +3.5dB response @ center freq
        0x06,   // +5.0dB response @ center freq
        0x07    // +6.0dB response @ center freq
    };

    _p_registers->lock();

    BYTE sharp_value;
    _p_registers->readByte(LUMA_CTRL_BYTE_3, &sharp_value);

    sharp_value &= ~0x07;
    sharp_value |= sharpness_mappings[new_sharpness];

    _p_registers->writeByte(LUMA_CTRL_BYTE_3, sharp_value);

    _p_registers->unlock();

    return TRUE;
}

/////////////////////////////////////////////////////////////////////////////////////////
VOID Thresher::enableVideoOutput()
{   
    // not used, same as corona
    _p_registers->lock();

    _p_registers->writeByte(TS1_PIN_CTL0,0xff);
    _p_registers->writeByte(TS1_PIN_CTL1,0x0f);
   
    
    _p_registers->unlock();
}

/////////////////////////////////////////////////////////////////////////////////////////
VOID Thresher::disableVideoOutput()
{
    // not used, same as corona
    _p_registers->lock();

    DWORD value;
    _p_registers->readDword(PIN_CTRL, &value);

    //Polaris remove these FLD
    //value &= ~(FLD_AGC_OUT_EN | FLD_VID_DATA_OUT_EN | FLD_VID_CTRL_OUT_EN);

    _p_registers->writeDword(PIN_CTRL, value);

    _p_registers->unlock();
}

/////////////////////////////////////////////////////////////////////////////////////////
// Handle any video-mode specific overrides that are different on a per video standards
// basis after touching the MODE_CTRL register which resets many values for autodetect
//
VOID Thresher::do_MODE_CTRL_overrides()
{
    DWORD value = 0;

    // Let the standard autodetect do its job before doing any overrides
    pauseThread(100);

    _p_registers->lock();

    // Change the DFE_CTRL3 bp_percent to fix flagging
    //_p_registers->readModifyWriteDword(DFE_CTRL3, FLD_DCC_LOOP_GAIN, 0x00 );
    // as per Kaelan to improve secam perfermance
    _p_registers->writeDword(DFE_CTRL3,0xCD3F0280);

    // Rev A CX23888 and all CX23885
    switch (_video_mode)
    {
        case VIDEO_MODE_NTSC:
            DbgLog(("do_MODE_CTRL_overrides NTSC\n"));

            // Move the close caption lines out of active video, adjust the active video start point
            _p_registers->readModifyWriteDword(VERT_TIM_CTRL, FLD_VBLANK_CNT, 0x1A );
            _p_registers->readModifyWriteDword(VERT_TIM_CTRL, FLD_VACTIVE_CNT, 0x1E6000 );
            _p_registers->readModifyWriteDword(VERT_TIM_CTRL, FLD_V656BLANK_CNT, 0x1E000000 );

            _p_registers->readModifyWriteDword(HORIZ_TIM_CTRL, FLD_HBLANK_CNT,_p_registers->Set_Field(FLD_HBLANK_CNT, 0x7F));
            break;

        case VIDEO_MODE_PAL:
        case VIDEO_MODE_PAL_N:
        case VIDEO_MODE_PAL_NC:
            DbgLog(("do_MODE_CTRL_overrides PAL\n"));
            _p_registers->readModifyWriteDword(VERT_TIM_CTRL, FLD_VBLANK_CNT, 0x24 );
            // Adjust the active video horizontal start point
            _p_registers->readModifyWriteDword(HORIZ_TIM_CTRL, FLD_HBLANK_CNT,_p_registers->Set_Field(FLD_HBLANK_CNT, 0x89));
            
            break;

        case VIDEO_MODE_SECAM:
            DbgLog(("do_MODE_CTRL_overrides SECAM\n"));
            _p_registers->readModifyWriteDword(VERT_TIM_CTRL, FLD_VBLANK_CNT, 0x24 );
            // Adjust the active video horizontal start point
            _p_registers->readModifyWriteDword(HORIZ_TIM_CTRL, FLD_HBLANK_CNT,_p_registers->Set_Field(FLD_HBLANK_CNT, 0x89));
            
            break;
    }
   
    
    _p_registers->unlock();
}

BOOLEAN Thresher::IsVideoPresent()
{
    DWORD   gen_stat;
    BOOLEAN video_locked;
    _p_registers->readDword(GEN_STAT, &gen_stat);
    return video_locked = ((gen_stat & FLD_VLOCK) == 0) ? FALSE : TRUE;  // VLock
}

BOOLEAN Thresher::GetVideoLock()
{
    DWORD   gen_stat;
    BOOLEAN video_locked;
    _p_registers->readDword(GEN_STAT, &gen_stat);

    DbgLog(("Thresher::GetVideoLock GEN_STAT = 0x%x\n",gen_stat));
    
    return video_locked =
        ((gen_stat & FLD_VPRES) &&    // video present
         (gen_stat & FLD_AGC_LOCK));  // AGC Lock
    

}

DWORD Thresher::caliberateDroopComp()
{    
    // Poalris do not use Droop comp    
    return(0);    
}

/////////////////////////////////////////////////////////////////////////////////////////
//Thresher::setupHTL_CTRL
//
//  Description : If we have to change the default KdKi values 0x0802 (such as for 888/887 tuner
//                Input we have to) to something else then we have to make sure that the
//                new values are applied after Thresher has got a lock
//
/////////////////////////////////////////////////////////////////////////////////////////
void Thresher::setupHTL_CTRL()
{
    if (_video_input == VIDEO_INPUT_TUNER )
    {
        DWORD oldValue = 0;
        DWORD value = 0;

        _p_registers->readDword(HTL_CTRL, &oldValue);

        // If the value read is not the default
        if ((oldValue & 0x0000FFFF) != 0x0802)
        {
            DWORD counter = 0;

            // first set the default
            value = oldValue;
            value &= 0xFFFF0000;    // clear Kd Ki default values
            value |= 0x00000802;    // change Kd Ki values
            _p_registers->writeDword(HTL_CTRL, value);
            //Give a delay of about 25ms
            pauseThread(25);
            // Now if we have VideoLock, then we will set it to the modified value
            while (counter < 3)
            {
                if(!GetVideoLock())
                {
                    // Try again
                    pauseThread(5);
                    counter++;
                }
                else
                {
                    // Got Video lock
                    _p_registers->writeDword(HTL_CTRL, oldValue);
                    //bail out
                    break;
                }
            }  // end of while loop
        } // end of If ((oldValue & 0x0000FFFF) != 0x0802) clause
    }
}



⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -