tinySG/MDK-ARM/lmx2595.c
2025-01-08 00:18:38 +08:00

805 lines
20 KiB
C
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#include "stm32f0xx.h"
#include "main.h"
#include "lmx2595.h"
uint16_t debug_outen=0;
_LMX2595_REG lmx;
static LMX_MAP_T sLMX_MAP_T = {
//sck
{
GPIOA,
LL_GPIO_PIN_5,
},
//sdi
{
GPIOA,
LL_GPIO_PIN_7,
},
//csb
{
GPIOA,
LL_GPIO_PIN_4,
},
//ldo
{
GPIOA,
LL_GPIO_PIN_6,
}
};
unsigned char gLmxLdSta = 0x00;
static void DELAY_Nop(uint32_t num)
{
while(num--)
{
__NOP();
}
}
void Lmx_CSB_SET(void)
{
LL_GPIO_SetOutputPin(sLMX_MAP_T.CSB.gpio, sLMX_MAP_T.CSB.gpio_pin);
}
void Lmx_CSB_RESET(void)
{
LL_GPIO_ResetOutputPin(sLMX_MAP_T.CSB.gpio, sLMX_MAP_T.CSB.gpio_pin);
}
void Lmx_SCK_SET(void)
{
LL_GPIO_SetOutputPin(sLMX_MAP_T.SCK.gpio, sLMX_MAP_T.SCK.gpio_pin);
}
void Lmx_SCK_RESET(void)
{
LL_GPIO_ResetOutputPin(sLMX_MAP_T.SCK.gpio, sLMX_MAP_T.SCK.gpio_pin);
}
void Lmx_SDI_SET(void)
{
LL_GPIO_SetOutputPin(sLMX_MAP_T.SDI.gpio, sLMX_MAP_T.SDI.gpio_pin);
}
void Lmx_SDI_RESET(void)
{
LL_GPIO_ResetOutputPin(sLMX_MAP_T.SDI.gpio, sLMX_MAP_T.SDI.gpio_pin);
}
uint8_t spi_8bit(uint8_t dat)
{
uint8_t rCtrlSpiCodeB;
uint8_t i;
uint8_t B_Miso = 0x00;
rCtrlSpiCodeB = dat;
for(i=0;i<8;i++)
{
B_Miso = (B_Miso<<0x01);
if((rCtrlSpiCodeB&0x80) == 0x00)
{
Lmx_SDI_RESET();
}
else
{
Lmx_SDI_SET();
}
Lmx_SCK_RESET();
DELAY_Nop(100);
Lmx_SCK_SET();
DELAY_Nop(100);
//上升沿后微小延时读取MISO数据//
B_Miso = (LL_GPIO_ReadInputPort(sLMX_MAP_T.LDO.gpio) & (0x01<< 6));
Lmx_SCK_RESET();
rCtrlSpiCodeB = (rCtrlSpiCodeB<<1);
}
return B_Miso;
}
uint16_t spi_16bit(uint16_t dat)
{
uint16_t rCtrlSpiCodeW;
uint8_t i;
uint16_t W_Miso = 0x00;
rCtrlSpiCodeW = dat;
for(i=0;i<16;i++)
{
W_Miso = (W_Miso<<0x0001);
if((rCtrlSpiCodeW&0x8000) == 0x0000)
{
Lmx_SDI_RESET();
}
else
{
Lmx_SDI_SET();
}
Lmx_SCK_RESET();
DELAY_Nop(100);
Lmx_SCK_SET();
//上升沿后微小延时读取MISO数据//
W_Miso = (W_Miso | (LL_GPIO_ReadInputPort(sLMX_MAP_T.LDO.gpio)& (0x01<<6)));
DELAY_Nop(100);
Lmx_SCK_RESET();
rCtrlSpiCodeW = (rCtrlSpiCodeW<<1);
}
return W_Miso;
}
//对器件进行读操作,输入为寄存器地址,返回读出的数据//
uint16_t lmxRead(uint8_t regadr)
{
uint16_t rddat;
regadr = regadr|0x80; //将寄存器地址最高位置1确保为读操作//
Lmx_CSB_RESET(); //片选信号拉低//
DELAY_Nop(50);
Lmx_SCK_RESET();
DELAY_Nop(50);
spi_8bit(regadr); //送出地址//
rddat=spi_16bit(0); //送出16位无效数据用于回读寄存器数据//
DELAY_Nop(50);
Lmx_CSB_SET(); //片选失效//
return rddat;
}
void LmxWrite(uint8_t regadr,uint16_t dat)
{
regadr=regadr&0x7f; //将寄存器地址最高位置0确保为写操作//
Lmx_CSB_RESET(); //片选信号拉低//
DELAY_Nop(50);
Lmx_SCK_RESET();
DELAY_Nop(50);
spi_8bit(regadr); //送出地址//
spi_16bit(dat); //送出数据//
DELAY_Nop(50);
Lmx_CSB_SET(); //片选失效//
}
void LmxPortReset(void)
{
Lmx_CSB_SET(); //片选失效//
Lmx_SCK_RESET();
Lmx_SDI_RESET();
}
void Lmx_PortIntit(void)
{
LL_GPIO_InitTypeDef GPIO_InitStruct = {0};
GPIO_InitStruct.Pin = LL_GPIO_PIN_2;
GPIO_InitStruct.Mode = LL_GPIO_MODE_OUTPUT;
GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_HIGH;
GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
GPIO_InitStruct.Pull = LL_GPIO_PULL_UP;
LL_GPIO_Init(GPIOA, &GPIO_InitStruct);
GPIO_InitStruct.Pin = LL_GPIO_PIN_3;
GPIO_InitStruct.Mode = LL_GPIO_MODE_OUTPUT;
GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_HIGH;
GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
GPIO_InitStruct.Pull = LL_GPIO_PULL_UP;
LL_GPIO_Init(GPIOA, &GPIO_InitStruct);
GPIO_InitStruct.Pin = LL_GPIO_PIN_4;
GPIO_InitStruct.Mode = LL_GPIO_MODE_OUTPUT;
GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_HIGH;
GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
GPIO_InitStruct.Pull = LL_GPIO_PULL_UP;
LL_GPIO_Init(GPIOA, &GPIO_InitStruct);
GPIO_InitStruct.Pin = LL_GPIO_PIN_5;
GPIO_InitStruct.Mode = LL_GPIO_MODE_OUTPUT;
GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_HIGH;
GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
GPIO_InitStruct.Pull = LL_GPIO_PULL_UP;
LL_GPIO_Init(GPIOA, &GPIO_InitStruct);
GPIO_InitStruct.Pin = LL_GPIO_PIN_6;
GPIO_InitStruct.Mode = LL_GPIO_MODE_INPUT;
GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_LOW;
GPIO_InitStruct.Pull = LL_GPIO_PULL_UP;
LL_GPIO_Init(GPIOA, &GPIO_InitStruct);
GPIO_InitStruct.Pin = LL_GPIO_PIN_7;
GPIO_InitStruct.Mode = LL_GPIO_MODE_OUTPUT;
GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_HIGH;
GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
GPIO_InitStruct.Pull = LL_GPIO_PULL_UP;
LL_GPIO_Init(GPIOA, &GPIO_InitStruct);
LmxPortReset();
}
void SetLmxParameter(void)
{
lmx.LMX_R70.All= 0x0000;
lmx.LMX_R69.All= 0x0000;
lmx.LMX_R68.All= 0x0089;
lmx.LMX_R64.All= 0x0377;
lmx.LMX_R62.All= 0x0000;
lmx.LMX_R61.All= 0x0001;
lmx.LMX_R59.All= 0x0000;
lmx.LMX_R48.All= 0x03FC;
lmx.LMX_R47.All= 0x08D4;
lmx.LMX_R46.All= 0x1E21;
lmx.LMX_R45.All= 0x0000;
lmx.LMX_R44.All= 0x0000;
lmx.LMX_R43.All= 0x0008;
lmx.LMX_R42.All= 0x0000;
lmx.LMX_R41.All= 0x0001;
lmx.LMX_R40.All= 0x0000;
lmx.LMX_R39.All= 0x8104;
lmx.LMX_R38.All= 0x0960;
lmx.LMX_R37.All= 0x5000;
lmx.LMX_R36.All= 0x0821;
lmx.LMX_R35.All= 0x109F;
lmx.LMX_R34.All= 0xC3EA;
lmx.LMX_R33.All= 0x2A0A;
lmx.LMX_R32.All= 0x210A;
lmx.LMX_R31.All= 0x0401;
lmx.LMX_R30.All= 0x0034;
lmx.LMX_R29.All= 0x0084;
lmx.LMX_R28.All= 0x2924;
lmx.LMX_R25.All= 0x0000;
lmx.LMX_R24.All= 0x0509;
lmx.LMX_R23.All= 0x8842;
lmx.LMX_R22.All= 0x2300;
lmx.LMX_R20.All= 0x012C;
lmx.LMX_R19.All= 0x0965;
lmx.LMX_R14.All= 0x0318;
lmx.LMX_R13.All= 0x4003;
lmx.LMX_R12.All= 0x700A;
lmx.LMX_R11.All= 0x0018;
lmx.LMX_R10.All= 0x10D8;
lmx.LMX_R9.All =0x0302;
lmx.LMX_R8.All =0x1084;
lmx.LMX_R7.All =0x28B2;
lmx.LMX_R4.All =0x0C43;
lmx.LMX_R2.All =0x0500;
lmx.LMX_R1.All =0x080A;
lmx.LMX_R0.All =0x2278;
/*
lmx.LMX_R112.All = 0x0000;
lmx.LMX_R111.All = 0x0000;
lmx.LMX_R110.All = 0x0000;
lmx.LMX_R109.All = 0x0000;
lmx.LMX_R108.All = 0x0000;
lmx.LMX_R107.All = 0x0000;
lmx.LMX_R106.All = 0x0000;
lmx.LMX_R105.All = 0x0021;
lmx.LMX_R104.All = 0x0000;
lmx.LMX_R103.All = 0x0000;
lmx.LMX_R102.All = 0x3F80;
lmx.LMX_R101.All = 0x0011;
lmx.LMX_R100.All = 0x0000;
lmx.LMX_R99.All = 0x0000 ;
lmx.LMX_R98.All = 0x0200 ;
lmx.LMX_R97.All = 0x0888 ;
lmx.LMX_R96.All = 0x0000 ;
lmx.LMX_R95.All = 0x0000 ;
lmx.LMX_R94.All = 0x0000 ;
lmx.LMX_R93.All = 0x0000 ;
lmx.LMX_R92.All = 0x0000 ;
lmx.LMX_R91.All = 0x0000 ;
lmx.LMX_R90.All = 0x0000 ;
lmx.LMX_R89.All = 0x0000 ;
lmx.LMX_R88.All = 0x0000 ;
lmx.LMX_R87.All = 0x0000 ;
lmx.LMX_R86.All = 0xFFFF ;
lmx.LMX_R85.All = 0xD2FF ;
lmx.LMX_R84.All = 0x0001 ;
lmx.LMX_R83.All = 0x0000 ;
lmx.LMX_R82.All = 0x1E00 ;
lmx.LMX_R81.All = 0x0000 ;
lmx.LMX_R80.All = 0x6666 ;
lmx.LMX_R79.All = 0x0026 ;
lmx.LMX_R78.All = 0x0003 ;
lmx.LMX_R77.All = 0x0000 ;
lmx.LMX_R76.All = 0x000C ;
lmx.LMX_R75.All = 0x0B80 ;
lmx.LMX_R74.All = 0x0000 ;
lmx.LMX_R73.All = 0x003F ;
lmx.LMX_R72.All = 0x0001 ;
lmx.LMX_R71.All = 0x0081 ;
lmx.LMX_R70.All = 0xC350 ;
lmx.LMX_R69.All = 0x0000 ;
lmx.LMX_R68.All = 0x03E8 ;
lmx.LMX_R67.All = 0x0000 ;
lmx.LMX_R66.All = 0x01F4 ;
lmx.LMX_R65.All = 0x0000 ;
lmx.LMX_R64.All = 0x1388 ;
lmx.LMX_R63.All = 0x0000 ;
lmx.LMX_R62.All = 0x0322 ;
lmx.LMX_R61.All = 0x00A8 ;
lmx.LMX_R60.All = 0x0000 ;
lmx.LMX_R59.All = 0x0001 ;
lmx.LMX_R58.All = 0x9001 ;
lmx.LMX_R57.All = 0x0020 ;
lmx.LMX_R56.All = 0x0000 ;
lmx.LMX_R55.All = 0x0000 ;
lmx.LMX_R54.All = 0x0000 ;
lmx.LMX_R53.All = 0x0000 ;
lmx.LMX_R52.All = 0x0820 ;
lmx.LMX_R51.All = 0x0080 ;
lmx.LMX_R50.All = 0x0000 ;
lmx.LMX_R49.All = 0x4180 ;
lmx.LMX_R48.All = 0x0300 ;
lmx.LMX_R47.All = 0x0300 ;
lmx.LMX_R46.All = 0x07FC ;
lmx.LMX_R45.All = 0xC0FC ;
lmx.LMX_R44.All = 0x1FE3 ;
lmx.LMX_R43.All = 0x0000 ;
lmx.LMX_R42.All = 0x0000 ;
lmx.LMX_R41.All = 0x0000 ;
lmx.LMX_R40.All = 0x0000 ;
lmx.LMX_R39.All = 0x0001 ;
lmx.LMX_R38.All = 0x0000 ;
lmx.LMX_R37.All = 0x8304 ;
lmx.LMX_R36.All = 0x0300 ;
lmx.LMX_R35.All = 0x0004 ;
lmx.LMX_R34.All = 0x0000 ;
lmx.LMX_R33.All = 0x1E21 ;
lmx.LMX_R32.All = 0x0393 ;
lmx.LMX_R31.All = 0x43EC ;
lmx.LMX_R30.All = 0x318C ;
lmx.LMX_R29.All = 0x318C ;
lmx.LMX_R28.All = 0x0488 ;
lmx.LMX_R27.All = 0x0002 ;
lmx.LMX_R26.All = 0x0DB0 ;
lmx.LMX_R25.All = 0x0C2B ;
lmx.LMX_R24.All = 0x071A ;
lmx.LMX_R23.All = 0x007C ;
lmx.LMX_R22.All = 0x0001 ;
lmx.LMX_R21.All = 0x0401 ;
lmx.LMX_R20.All = 0xE048 ;
lmx.LMX_R19.All = 0x27B7 ;
lmx.LMX_R18.All = 0x0064 ;
lmx.LMX_R17.All = 0x012C ;
lmx.LMX_R16.All = 0x0080 ;
lmx.LMX_R15.All = 0x064F ;
lmx.LMX_R14.All = 0x1E70 ; //0x1E30:1.2mA 0x1E70: 1.5mA
lmx.LMX_R13.All = 0x4000 ;
lmx.LMX_R12.All = 0x5001 ;
lmx.LMX_R11.All = 0x0018 ;
lmx.LMX_R10.All = 0x10D8 ;
lmx.LMX_R9.All = 0x0604 ;
lmx.LMX_R8.All = 0x2000 ;
lmx.LMX_R7.All = 0x40B2 ;
lmx.LMX_R6.All = 0xC802 ;
lmx.LMX_R5.All = 0x00C8 ;
lmx.LMX_R4.All = 0x0A43 ;
lmx.LMX_R3.All = 0x0642 ;
lmx.LMX_R2.All = 0x0500 ;
lmx.LMX_R1.All = 0x0800 ;
lmx.LMX_R0.All = 0x2418 ;
*/
}
void SetLmxFreq(void)
{
LmxWrite(0,0x0002);//reset device
LL_mDelay(50);
/*
LmxWrite(112,lmx.LMX_R112.All);
LmxWrite(111,lmx.LMX_R111.All);
LmxWrite(110,lmx.LMX_R110.All);
LmxWrite(109,lmx.LMX_R109.All);
LmxWrite(108,lmx.LMX_R108.All);
LmxWrite(107,lmx.LMX_R107.All);
LmxWrite(106,lmx.LMX_R106.All);
LmxWrite(105,lmx.LMX_R105.All);
LmxWrite(104,lmx.LMX_R104.All);
LmxWrite(103,lmx.LMX_R103.All);
LmxWrite(102,lmx.LMX_R102.All);
LmxWrite(101,lmx.LMX_R101.All);
LmxWrite(100,lmx.LMX_R100.All);
LmxWrite(99,lmx.LMX_R99.All);
LmxWrite(98,lmx.LMX_R98.All);
LmxWrite(97,lmx.LMX_R97.All);
LmxWrite(96,lmx.LMX_R96.All);
LmxWrite(95,lmx.LMX_R95.All);
LmxWrite(94,lmx.LMX_R94.All);
LmxWrite(93,lmx.LMX_R93.All);
LmxWrite(92,lmx.LMX_R92.All);
LmxWrite(91,lmx.LMX_R91.All);
LmxWrite(90,lmx.LMX_R90.All);
LmxWrite(89,lmx.LMX_R89.All);
LmxWrite(88,lmx.LMX_R88.All);
LmxWrite(87,lmx.LMX_R87.All);
LmxWrite(86,lmx.LMX_R86.All);
LmxWrite(85,lmx.LMX_R85.All);
LmxWrite(84,lmx.LMX_R84.All);
LmxWrite(83,lmx.LMX_R83.All);
LmxWrite(82,lmx.LMX_R82.All);
LmxWrite(81,lmx.LMX_R81.All);
LmxWrite(80,lmx.LMX_R80.All);
LmxWrite(79,lmx.LMX_R79.All);
LmxWrite(78,lmx.LMX_R78.All);
LmxWrite(77,lmx.LMX_R77.All);
LmxWrite(76,lmx.LMX_R76.All);
LmxWrite(75,lmx.LMX_R75.All);
LmxWrite(74,lmx.LMX_R74.All);
LmxWrite(73,lmx.LMX_R73.All);
LmxWrite(72,lmx.LMX_R72.All);
LmxWrite(71,lmx.LMX_R71.All);
*/
LmxWrite(70,lmx.LMX_R70.All);
LmxWrite(69,lmx.LMX_R69.All);
LmxWrite(68,lmx.LMX_R68.All);
LmxWrite(64,lmx.LMX_R64.All);
LmxWrite(62,lmx.LMX_R62.All);
LmxWrite(61,lmx.LMX_R61.All);
LmxWrite(59,lmx.LMX_R59.All);
LmxWrite(48,lmx.LMX_R48.All);
LmxWrite(47,lmx.LMX_R47.All);
LmxWrite(46,lmx.LMX_R46.All);
LmxWrite(45,lmx.LMX_R45.All);
LmxWrite(44,lmx.LMX_R44.All);
LmxWrite(43,lmx.LMX_R43.All);
LmxWrite(42,lmx.LMX_R42.All);
LmxWrite(41,lmx.LMX_R41.All);
LmxWrite(40,lmx.LMX_R40.All);
LmxWrite(39,lmx.LMX_R39.All);
LmxWrite(38,lmx.LMX_R38.All);
LmxWrite(37,lmx.LMX_R37.All);
LmxWrite(36,lmx.LMX_R36.All);
LmxWrite(35,lmx.LMX_R35.All);
LmxWrite(34,lmx.LMX_R34.All);
LmxWrite(33,lmx.LMX_R33.All);
LmxWrite(32,lmx.LMX_R32.All);
LmxWrite(31,lmx.LMX_R31.All);
LmxWrite(30,lmx.LMX_R30.All);
LmxWrite(29,lmx.LMX_R29.All);
LmxWrite(28,lmx.LMX_R28.All);
LmxWrite(25,lmx.LMX_R25.All);
LmxWrite(24,lmx.LMX_R24.All);
LmxWrite(23,lmx.LMX_R23.All);
LmxWrite(22,lmx.LMX_R22.All);
LmxWrite(21,lmx.LMX_R21.All);
LmxWrite(20,lmx.LMX_R20.All);
LmxWrite(19,lmx.LMX_R19.All);
LmxWrite(14,lmx.LMX_R14.All);
LmxWrite(13,lmx.LMX_R13.All);
LmxWrite(12,lmx.LMX_R12.All);
LmxWrite(11,lmx.LMX_R11.All);
LmxWrite(10,lmx.LMX_R10.All);
LmxWrite(9,lmx.LMX_R9.All);
LmxWrite(8,lmx.LMX_R8.All);
LmxWrite(7,lmx.LMX_R7.All);
LmxWrite(3,lmx.LMX_R3.All);
LmxWrite(2,lmx.LMX_R2.All);
LmxWrite(1,lmx.LMX_R1.All);
LmxWrite(0,lmx.LMX_R0.All);
DELAY_Nop(500000);
LmxWrite(0,lmx.LMX_R0.All);
}
//check LD
//configure the register again,when check the LD is low
void ConfigLmxAgain(void)
{
uint8_t LmxLdSta = 0x00;
static uint8_t sChkLdDone = 0x00;
gLmxLdSta = LL_GPIO_ReadInputPort(sLMX_MAP_T.LDO.gpio) &( 0x01 << sLMX_MAP_T.LDO.gpio_pin);
//if(sChkLdDone != 0x00)
//return;
LmxLdSta = LL_GPIO_ReadInputPort(sLMX_MAP_T.LDO.gpio) & (0x01<<sLMX_MAP_T.LDO.gpio_pin);
if(LmxLdSta != 0x00)
return;
SetLmxFreq();
sChkLdDone = 0xaa;
}
void LMX2592_Wchannel_div(uint16_t chdiv_num){
switch(chdiv_num){
case 2:
LmxWrite(35,0x001B);
LmxWrite(36,0x0C10);
break;
case 3:
LmxWrite(35,0x001d); //ti lmx2592 datasheet has an error in REG35 !!!!
LmxWrite(36,0x0C10);
break;
case 4:
LmxWrite(35,0x029B);
LmxWrite(36,0x0C20);
break;
case 6:
LmxWrite(35,0x029d);
LmxWrite(36,0x0C20);
break;
case 8:
LmxWrite(35,0x049B);
LmxWrite(36,0x0C20);
break;
case 12:
LmxWrite(35,0x049d);
LmxWrite(36,0x0C20);
break;
case 16:
LmxWrite(35,0x109B);
LmxWrite(36,0x0C20);
break;
case 24:
LmxWrite(35,0x109d);
LmxWrite(36,0x0C20);
break;
case 32:
LmxWrite(35,0x119B);
LmxWrite(36,0x0C41);
break;
case 36:
LmxWrite(35,0x099d);
LmxWrite(36,0x0C41);
break;
case 48:
LmxWrite(35,0x119d);
LmxWrite(36,0x0C41);
break;
case 64:
LmxWrite(35,0x119B);
LmxWrite(36,0x0C42);
break;
case 96:
LmxWrite(35,0x119B);
LmxWrite(36,0x0C44);
break;
case 128:
LmxWrite(35,0x119B);
LmxWrite(36,0x0C48);
break;
case 192:
LmxWrite(35,0x119d);
LmxWrite(36,0x0C48);
break;
default:
LmxWrite(35,0x119B);
LmxWrite(36,0x0C48);
}
}
void LMX2592_FIND_CHANNEL_DIV(float freq,uint16_t *chdiv_num,uint16_t *vco_doubler,uint16_t *vco_level){
if(freq>9800){
}
else if(freq>7100){
*chdiv_num = 1; //disable chdiv
*vco_doubler=1;//enable vco doubler
*vco_level=0;
}
else if(freq>6500){
*chdiv_num = 1; //disable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=1;//high level (REG30 7:6)
}
else if(freq>3550){
*chdiv_num = 1; //disable chdiv
*vco_doubler=0;//disable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>1775){
*chdiv_num = 2; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>1184){
*chdiv_num = 3; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>888){
*chdiv_num = 4; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>592){
*chdiv_num = 6; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>444){
*chdiv_num = 8; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>296){
*chdiv_num = 12; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>222){
*chdiv_num = 16; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>148){
*chdiv_num = 24; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>111){
*chdiv_num = 32; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>99){
*chdiv_num = 36; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>74){
*chdiv_num = 48; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>56){
*chdiv_num = 64; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>37){
*chdiv_num = 96; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>28){
*chdiv_num = 128; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else if(freq>=20){
*chdiv_num = 192; //enable chdiv
*vco_doubler=0;//enable vco doubler
*vco_level=0;//low level (REG30 7:6)
}
else{
}
}
uint16_t REG46=0x1424;
uint16_t REG47=0x08D4;
uint16_t REG48=0x03FD;
void LMX2592_SETOUT(uint16_t channel ,uint16_t state){
if(channel == 1){//cha
if(state) REG47 = (REG47 & 0xEFFF);
else REG47 = (REG47 & 0xEFFF) | 0x1000;
LmxWrite(47,REG47);
}
if(channel == 2){//chb
if(state) REG48 = (REG48 & 0xFFFD);
else REG48 = (REG48 & 0xFFFD) | 0x0002;
LmxWrite(48,REG48);
}
}
void LMX2592_WRITE_FREQ(double freq){
// Fvco = Fpd x PLL_N_PRE x (PLL_N + PLL_NUM / PLL_DEN)
// The VCO core covers an octave from 3.55 to 7.1 GHz.
// F_PFD=20Mhz Fout = pfd * (N) / channel_div; input freq is in Mhz
// denominator = 20M(0x0131 2D00 ) the resolution = 1Hz
uint16_t chdiv_num;
uint16_t vco_doubler;
uint16_t vco_level;
uint16_t FPFD=20;
LMX2592_FIND_CHANNEL_DIV(freq,&chdiv_num,&vco_doubler,&vco_level);
if(freq>5000){//pfd=5Mhz
FPFD=5;
LmxWrite(0,0x2206); //reset device; en ld;power up
LmxWrite(1,0x0808);//cal_clk div=1;cal clk = 10Mhz
LmxWrite(10,0x10d8);//disable multiplier
//LmxWrite(9,0x0b02);
LmxWrite(12,0x7002);//pll r pre div =2
LmxWrite(11,0x0018);//pll r div =1; set pfd = 20Mhz
}
else{//pfd=1Mhz
FPFD=1;
LmxWrite(0,0x2206); //reset device; en ld; pfd>10M;power up
LmxWrite(1,0x0808);//cal_clk div=1;cal clk = 10Mhz
LmxWrite(10,0x10d8);//disable multiplier
LmxWrite(12,0x700A);//pll r pre div =10 1
LmxWrite(11,0x0018);//pll r div =1; set pfd = 1Mhz 1
}
LmxWrite(37,0x5000); // presacle 4 1
LmxWrite(39,0x8104);
LmxWrite(14,0x0841); // 1.25 MA
/****************** OUTPUT PART ********************/
if(chdiv_num == 1){ // Direct out through VCO
if(vco_doubler == 1){
LmxWrite(30,0x0135);//enable vco doubler
freq = freq/2;
}
else if(vco_level){
LmxWrite(30,0x01F4);//level = high( fvco>6500Mhz)
}
else {
LmxWrite(30,0x0134);//level = low( fvco<6500Mhz)
}
LmxWrite(35,0x0019);//div0
LmxWrite(34,0xC3CA);// dis channel divider
LmxWrite(31,0x0081);//
LmxWrite(36,0x0000);//dis channel and out
LmxWrite(46,REG46);// A level=20 ;dis out a & b; MASH_ORDER=3
REG47 = (REG47 & 0xF7FF) | 0x0800;
LmxWrite(47,REG47);//Selects output from VCO
REG48 = (REG48 & 0xFFFE) | 0x0001;
LmxWrite(48,REG48); //Selects output from VCO
}
else {// use channel divider
LmxWrite(13,4003);
LmxWrite(30,0x0034);//level = low( fvco<6500Mhz) DIS vco doubler
LmxWrite(31,0x0601);//dis vco buffer; en channel buffer 1
LmxWrite(34,0xC3EA);// en channel divider
LmxWrite(46,REG46);// A level=20 ;dis out a & b; MASH_ORDER=3
REG47 = (REG47 & 0xF7FF) | 0x0000;
LmxWrite(47,REG47);//Selects A output from channel divider
REG48 = (REG48 & 0xFFFE);
LmxWrite(48,REG48); //Selects B output from channel divider
//write channel divider
LMX2592_Wchannel_div(chdiv_num);
}
/****************** NDIV SET ********************/
double N_DIV = freq * (double)chdiv_num ;
N_DIV = N_DIV/(FPFD);
N_DIV = N_DIV/4;
uint16_t N_integer = (uint16_t)N_DIV;
double N_fraction = N_DIV - (double)N_integer;
//write N_integer
N_integer = (N_integer<<1)&(0x1FFE);//save 12bit
LmxWrite(38,(N_integer));// pll Integer part of N-divider
//write N_fraction
N_fraction = N_fraction * 20000000;
uint32_t N_frac_REG = (uint32_t)N_fraction;
LmxWrite(44,(N_frac_REG>>16));//Numerator MSB of N-divider fraction
LmxWrite(45,N_frac_REG);//Numerator LSB of N-divider fraction
//LmxWrite(40,0x0131);//Denominator MSB of N-divider fraction
//LmxWrite(41,0x2d00);//Denominator LSB of N-divider fraction
LmxWrite(40,0x0131);//Denominator MSB of N-divider fraction
LmxWrite(41,0x2d00);//Denominator LSB of N-divider fraction
//LmxWrite(47,0x18D4);
/****************** STRAT WORK ********************/
if(FPFD == 1)
LmxWrite(0,0x2278); //set pfd < 2.5Mhz
else
LmxWrite(0,0x220c | 0X0020);
}