圣源电子制作

 找回密码
 立即注册
查看: 11594|回复: 0
打印 上一主题 下一主题

基于PIC WWVB时钟-自动校准时间-原理图-PCB-C程序-转载外国网站

[复制链接]
跳转到指定楼层
楼主
发表于 2011-11-10 19:38:31 | 只看该作者 |只看大图 回帖奖励 |倒序浏览 |阅读模式



  WWVB在网络上的时钟设计DIY有很多版本。 商业的“原子”时钟是便宜和广泛使用,但我想我的手,在设计一个获得接收到WWVB的洞察力和了解PIC单片机编程的一个小尝试。 我的版本是不是最简单的,但它工作得很好,我认为它提供了一些独特的功能.

WWVB时钟功能
  • 接收时间播出,WWVB,柯林斯堡,CO
  •   WWVB时间自动同步与内部时间
  •   WWVB信号丢失时保持本地时间
  •   这个版本是太平洋标准时间,并自动检测/纠正Daylignt储蓄的时间
  •   6位数字显示小时,分钟,秒使用1“七段LED显示
  •   WWVB同步指示器
  •   时间显示在12小时格式
  •   的PIC 16F628单片机
  •   C语言编写的软件
  •   所有工具(原理图编辑器,C编译器,PCB布局软件,PIC的程序员都是免费的,在网络上可供下载。

  的完整描述和规范WWVB广播(免费), WWVB信号播出时间为60 kHz载波AM调制代码帧,每分钟更新一次。  数据传输速率是一个比特每秒。  随着时间码信息,数据帧还包含同步位,日历数据,UT1之修正,闰年,闰秒的数据 。  这里介绍的时钟设计只解码数据的时间和夏令时的校正数据 。  该软件可以很容易地进行修改,包括其他信息位解码,如果需要的话。  低频WWVB信号强度较弱和接收可能会出现问题。  信号采集时间是可变的,位置和大气条件而定 。  接待处通常情况下,最好在晚上八时至晚上-上午04时。  要使用的时钟,只需接通电源,并等待接收WWVB信号 。  时钟接收到一个完整的无差错的数据帧时,它会自动重置显示,以显示正确的时间 。  在最初的时间校正,时钟将保持一段时间,即使失去WWVB接待。


硬件描述
                        
     在原理图(PDF格式)所示,在时钟的心脏是一个PIC 16F628单片机运行在4 MHz 。  解码的实时数据依次从微控制器的输出(RA0 - RA3)到7段解码器/驱动程序上的4位数据总线。  数据输出顺序为秒,分,秒,分钟,小时和10小时10秒10。  微控制器输出(RB1,RB2,RB3)路由10微秒stroble的脉冲RB4的出到7段解码器/驱动程序,在适当的时间锁存数据总线值。  秒和10秒显示值每秒更新一次。  分钟,10分钟,小时和10小时,每分钟更新一次。  显示由1“橘红色的LED七段显示器上显示的小数点用来形成冒号分开秒,分钟和小时10秒和10分钟显示安装倒挂形成上部的结肠点。WWVB接收器是一个C - MAX模型CMMR - 6从DIGI - KEY                一部分#561 - 1014 - ND loopstick天线完成。  从接收器输出的数据进行采样RB0的微控制器

  我已经建立了两个时钟,一个点,以点布线和使用PCB。  两个版本都表现良好。  只要保持接收器远离噪声源和电线/走线长度尽可能短,以减小电感。  我发现接收器也是由电源产生的磁场敏感 。  我用一个9V,200毫安,而不是一个内部电源“壁疣”,以消除这个问题。
  我的PCB设计使用免费PCB软件 艺术品包含的主板和显示在一个单一的布局,以节省两个单独的电路板的成本板。   发送Gerber文件和使用他们的“裸骨”的过程 。  “裸骨”的过程,不包括阻焊也不丝网。  切断主电路板显示板和主板安装直角和线一起使用提供的垫

软件简介  
我用C编译器源升压开发软件。 它是免费提供      
  该软件是中断驱动,从PIC定时器2模块。  基本时序设置为接收器采样和内部时间传播提供32个中断/秒。  接收到的数据进行采样,每秒32样本。  软件交叉关联存储的“理想”样本一,零,和同步模式的输入样本。  确定在连续两个连续的同步比特的数据帧的开始。  当检测到这种模式,秒的数据被重置为零,后续位或零的提取分钟和小时的数据检测 。  只有时间显示有关的数据进行解码。  内的数据帧不包含时间数据位被忽略。  31出32位检测互相关算法需要接收到的数据和存储的“理想”的同步模式之间的样本协定。
                                 开启时同步检测和关闭时同步丢失秒位数的小数点 。  位和零的检测需要28 32接收到的数据和存储的“理想”模式之间的样本协议 。  如果任何检测到的位不符合或超过相关阈值,整个画面被丢弃,并启动一个新的搜索帧同步 。  当成功侦破的一帧的时间内数据同步和数据纠正太平洋标准时间和夏令时。  该软件必须改变为其他时区的正确更正。  还纠正一个WWVB在每个数据帧开始的有效时间造成的偏移分钟的时间。  完全矫正的时间转换为12小时格式,然后更新内部的时间值。  如果WWVB信号丢失,内部时间继续从它是依赖PIC晶体振荡器WWVB,直到下一个数据帧接收和验证,传播时间 。  PIC16F628是使用WIN PIC软件,免费提供编程

C程序
  1. // **************** Problem Log **************
  2. //        1. Need to fix the display on turn-on so
  3. //                that all digits are blanked except the
  4. //                seconds count.
  5. //
  6. //        
  7. //         
  8. //
  9. //



  10. // ***************** Revisions *********************
  11. // Initial working program (N/C) 11/09/2008
  12. //
  13. // Rev. A: 11/11/08  Fixed one-minute error problem
  14. //                        caused by wwv message "on-time" at the
  15. //                        start of a new message













  16. #include <system.h>

  17. //Target PIC16F628 configuration word
  18. #pragma DATA _CONFIG, _PWRTE_OFF & _WDT_OFF & _XT_OSC & _CP_OFF

  19. //Set clock frequency
  20. #pragma CLOCK_FREQ        4000000


  21. // variable declarations
  22.         char varl@0x0E;        // TMR1L register absolute address
  23.         char varh@0x0F;        // TMR1H register absolute address        

  24.         // bit patterns for correlation per WWVB description
  25.         unsigned long sync = 0xFC000000;
  26.         unsigned long one =  0xFFFF0000;
  27.         unsigned long zero = 0xFFFFFF80;

  28.         unsigned long samples = 0;        // input sample register
  29.         unsigned long sync_temp;
  30.         unsigned char i;
  31.         unsigned char j;
  32.         unsigned char k;
  33.         unsigned char n;
  34.         unsigned char sync_count;
  35.         unsigned char one_count;
  36.         unsigned char zero_count;
  37.         unsigned char sync_threshold = 31;  // stringent sync threshold
  38.         unsigned char bit_threshold = 28;   // less stringent bit threshold
  39.         unsigned char sync_bit_1;
  40.         unsigned char sync_bit_2;
  41.         unsigned char sample_flag = 0;
  42.         unsigned char seconds = 0;
  43.         unsigned char ten_seconds = 0;
  44.         unsigned char seconds_counter = 0;
  45.         unsigned char seconds_temp = 0;
  46.         unsigned char local_hours;
  47.         unsigned char wwv_minutes;
  48.         unsigned char wwv_ten_minutes;
  49.         unsigned char wwv_hours;
  50.         unsigned char wwv_ten_hours;
  51.         unsigned char error;
  52.         unsigned char msg_valid = 0;
  53.         unsigned char internal_minutes_counter = 0;
  54.         unsigned char internal_ten_min = 0;
  55.         unsigned char internal_min = 0;
  56.         unsigned char internal_hours = 0;




  57. // *************************** sample() *******************
  58. //
  59. //        This routine collects samples from the wwvb receiver data
  60. //        output and places them into the sample register.  The sample
  61. //        register is a FIFO.
  62. //
  63. //        Called from: Interrupt service routine
  64. //
  65. // *******************************************

  66. sample()
  67.         {
  68.                 samples >>= 1;
  69.                 samples.31 = portb.0;
  70.                 sample_flag = 1;
  71.         }
  72. // ************************** end of sample() *****************


  73. // ****************** update_display() *************************
  74. //
  75. //        This routine writes minutes, ten minutes, hours, and ten hour
  76. //        data to the display drivers.
  77. //
  78. //        Parameters
  79. //                Entry: minutes, ten_minutes and hours from wwvb or from internal time
  80. //                Exit: none
  81. //
  82. //        Called from:        update_internal_time()
  83. //
  84. // ***************************************************************

  85. void update_display()

  86.         {
  87.                 unsigned char display_hours = 0;
  88.                 unsigned char display_ten_hours = 0;        
  89.                
  90.                 // convert hrs back to 2-byte format

  91.                 if (internal_hours == 0)
  92.                         display_hours = 2;
  93.         
  94.                 if ((internal_hours > 0) && (internal_hours < 10))
  95.                         display_hours = internal_hours;
  96.         
  97.                 if ((internal_hours > 9) && (internal_hours < 13))
  98.                         {
  99.                                 display_hours = internal_hours - 10;
  100.                                 display_ten_hours = 1;
  101.                         }
  102.         
  103.                 if ((internal_hours > 12) && (internal_hours < 22))
  104.                         {
  105.                                 display_hours = internal_hours - 12;
  106.                                 display_ten_hours = 0;
  107.                         }
  108.         
  109.                 if ((internal_hours > 21) && (internal_hours <= 23))
  110.                         {
  111.                                 display_hours = internal_hours - 22;
  112.                                 display_ten_hours = 1;
  113.                         }


  114.                         // port a values contain data for the 4511 display drivers
  115.                         // port b values are addresses for the hct138 1-8 decoder
  116.                         //        to distribute the strobes for the individual display
  117.                         //        digits.
  118.                         
  119.                         porta = internal_min;
  120.                         portb.1 = 0;
  121.                         portb.2 = 1;
  122.                         portb.3 = 0;
  123.                         portb.4 = 1;
  124.                         delay_us(10);
  125.                         portb.4 = 0;
  126.                                                                         
  127.                         porta = internal_ten_min;
  128.                         portb.1 = 1;
  129.                         portb.2 = 1;
  130.                         portb.3 = 0;
  131.                         portb.4 = 1;
  132.                         delay_us(10);
  133.                         portb.4 = 0;
  134.                         
  135.                         porta = display_hours;
  136.                         portb.1 = 0;
  137.                         portb.2 = 0;
  138.                         portb.3 = 1;
  139.                         portb.4 = 1;
  140.                         delay_us(10);
  141.                         portb.4 = 0;                                                               

  142.                         if (display_ten_hours != 1)
  143.                                 porta = 0x0F;        // this will cause the 4511 chip to blank the
  144.                                                                 // ten-hours digit
  145.                         else                                       
  146.                                 porta = display_ten_hours;

  147.                         portb.1 = 1;
  148.                         portb.2 = 0;
  149.                         portb.3 = 1;
  150.                         portb.4 = 1;
  151.                         delay_us(10);
  152.                         portb.4 = 0;               
  153.         }
  154. // ************************* end of update_display() *****************



  155. // *********************** update_internal_time() ******************
  156. //
  157. //        This routine keeps time either using the internal 32 sample/sec
  158. //        time base or wwv received time.  The time is in the following format:
  159. //
  160. //        internal_minutes: 0-9
  161. //        internal_ten_minutes: 0-5
  162. //        internal_hours: 0-23
  163. //
  164. //        Parameters
  165. //                Entry: none
  166. //                Exit: none
  167. //
  168. // ******************************************************************

  169. void update_internal_time()
  170.         {
  171.                 unsigned char temp_int_min = 0;
  172.                 unsigned char temp_internal_ten_minutes = 0;
  173.                 unsigned char temp_wwv_ten_min = 0;
  174.                
  175.                 if (msg_valid == 0)
  176.                         {
  177.                                 if (internal_minutes_counter < 59)
  178.                                         {
  179.                                                 internal_minutes_counter++;

  180.                                                 temp_int_min = internal_minutes_counter;
  181.                                                 internal_ten_min = 0;

  182.                                                 while( temp_int_min > 9)
  183.                                                         {
  184.                                                                 internal_ten_min++;
  185.                                                                 temp_int_min -= 10;
  186.                                                         }
  187.                                                 internal_min = temp_int_min;
  188.                                         }                                       
  189.                                 else        
  190.                                         {
  191.                                                 internal_minutes_counter = 0;
  192.                                                 internal_min = 0;
  193.                                                 internal_ten_min = 0;
  194.                                                 
  195.                                                 if (internal_hours < 23)
  196.                                                         internal_hours++;
  197.                                                 else
  198.                                                         internal_hours = 0;
  199.                                         }
  200.                         }
  201.                 else        // msg_valid == 1
  202.                         {
  203.                                 temp_wwv_ten_min = wwv_ten_minutes;
  204.                                 temp_internal_ten_minutes = 0;
  205.                                 while( temp_wwv_ten_min > 0 )
  206.                                         {
  207.                                                 temp_wwv_ten_min--;
  208.                                                 temp_internal_ten_minutes += 10;
  209.                                         }
  210.                                 internal_minutes_counter = temp_internal_ten_minutes + wwv_minutes;
  211.                                 internal_min = wwv_minutes;
  212.                                 internal_ten_min = wwv_ten_minutes;
  213.                                 internal_hours = local_hours;
  214.                         }
  215.                 update_display();
  216.                
  217.                 msg_valid = 0;
  218.         }

  219. // ************************* end of update_internal_time *************************




  220. // **********************************************************************************************
  221. //  Timer 1 interrupt handler.  This interrupt obtains new input data samples 32 times per second
  222. // **********************************************************************************************
  223. void interrupt( void )
  224. {
  225.         //Handle timer1 interrupt
  226.         if( pir1 & (1<<TMR1IF) )
  227.         {
  228.                 clear_bit( pir1, TMR1IF ); //clear timer 1 interrupt bit
  229.                 clear_bit( t1con, TMR1ON ); //stop timer 1
  230.                
  231.                 // load timer 1 with 0xC304
  232.                 varh = 0xC3;                // 0xC304 is an emperically adjusted
  233.                                                         // number to yield 32.0 samples/sec
  234.                 varl = 0x04;
  235.                 set_bit( t1con, TMR1ON ); //enable timer 1

  236.                 sample();                // "input sample routine

  237.                 // update "seconds" based on 32 sps interrupt rate
  238.                 if (n < 31)
  239.                         n++;
  240.                 else
  241.                         {
  242.                                 n = 0;
  243.                                 
  244.                                 if (seconds_counter < 59)
  245.                                         seconds_counter++;
  246.                                 else
  247.                                         {
  248.                                                 seconds_counter = 0;
  249.                                                 // propagate unsync internal time

  250.                                                 update_internal_time();
  251.                                         }
  252.                         
  253.                                 seconds_temp = seconds_counter;
  254.                                 ten_seconds = 0;
  255.                                 while (seconds_temp > 9)
  256.                                         {
  257.                                                 ten_seconds++;
  258.                                                 seconds_temp -= 10;
  259.                                         }
  260.                                 seconds = seconds_temp;
  261.         
  262.                                 porta = seconds;
  263.                                 clear_bit(portb, 1);
  264.                                 clear_bit(portb, 2);
  265.                                 clear_bit(portb, 3);                                       
  266.                                 set_bit(portb, 4);                                       
  267.                                 delay_10us(1);
  268.                                 clear_bit(portb, 4);
  269.                                                         
  270.                                 porta = ten_seconds;
  271.                                 portb.1 = 1;
  272.                                 portb.2 = 0;
  273.                                 portb.3 = 0;
  274.                                 portb.4 = 1;
  275.                                 delay_10us(1);
  276.                                 portb.4 = 0;
  277.                         }                        
  278.         }        
  279. }
  280. // ******************* end of timer 1 interrupt handler *****************




  281. // ************************** configure_mpu ***********************
  282. //
  283. //        Set up the 16F628 internal registers
  284. //
  285. //        Parameters
  286. //                Entry: none
  287. //                Exit: Registers set
  288. //
  289. //        Called from: Main()
  290. //
  291. // *****************************************************************
  292. void configure_mpu()
  293.         {
  294.                 //Configure port A
  295.                 trisa = 0x00;        // port a configured as outputs (except porta.5 which is
  296.                                                 // input only.
  297.                 //Configure port B
  298.                 trisb = 0xC1;        // port b 0, 6, and 7 are inputs
  299.                                                 // port b 1, 2, 3, 4, and 5 are outputs

  300.                 //Initialize port A
  301.                 porta = 0x00;
  302.                 //Initialize port B
  303.                 portb = 0x00;


  304.                 cmcon = 7; //disable comparators

  305.                 //Set Timer0 mode

  306.                 clear_bit( option_reg, T0CS ); //configure timer0 as a timer
  307.                 //Set prescaler assignment
  308.                 clear_bit( option_reg, PSA ); //prescaler is assigned to timer0
  309.                 //Set prescaler rate
  310.                 clear_bit( option_reg, PS2 ); //prescaler rate 1:2
  311.                 clear_bit( option_reg, PS1 );
  312.                 clear_bit( option_reg, PS0 );
  313.                 //Set timer0 source edge selection
  314.                 set_bit( option_reg, T0SE ); //increment on high-to-low transition on RA4/T0CKI pin

  315.                 //Set timer 1 prescaler rate
  316.                 clear_bit( t1con, T1CKPS1 ); //prescaler rate 1:2
  317.                 set_bit( t1con, T1CKPS0 );
  318.                 //Set timer 1 mode
  319.                 clear_bit( t1con, TMR1CS ); //Internal clock (FOSC/4)

  320.                 clear_bit( pir1, TMR1IF ); //clear timer 1 interrupt bit
  321.                 clear_bit( t1con, TMR1ON ); //stop timer 1
  322.                 varh = 0xC3;                // 0xC301 is a adjusted number to yield 32.0 samples/sec
  323.                 varl = 0x01;
  324.                 set_bit( t1con, TMR1ON ); //enable timer 1
  325.         
  326.                 //Set timer 2 prescaler rate
  327.                 clear_bit( t2con, T2CKPS1 ); //prescaler rate 1:1
  328.                 clear_bit( t2con, T2CKPS0 );
  329.                 //Set timer 2 postscaler rate
  330.                 clear_bit( t2con, TOUTPS3 ); //postscaler rate 1:1
  331.                 clear_bit( t2con, TOUTPS2 );
  332.                 clear_bit( t2con, TOUTPS1 );
  333.                 clear_bit( t2con, TOUTPS0 );
  334.                 //Set timer 2 mode (enable or disable)
  335.                 clear_bit( t2con, TMR2ON ); //enable timer 2

  336.                 //Enable interrupts (Timer1)
  337.                 intcon = 0xC0;  // enable global interrupts, disable timer0 interrupt bit
  338.                 pie1 = 0x01;        // enable timer1 overflow interrupt bit
  339.         }
  340. // ***************************** end of configure_mpu() *****************







  341. // ************************ find_sync() *************************
  342. //
  343. //        This routine correlates the sample register with the wwvb 2 bit
  344. //        sync sequence that starts each message.  The first bit looks for
  345. //        correlation on a bit-by-bit basis.  Once the first sync bit is
  346. //        detected, the second bit is tested as a complete 32-bit word.
  347. //        Sync is declared when both sync bits pass the sync threshold test
  348. //
  349. //        Parameters:
  350. //                Entry: sync_bit_1 and sync_bit_2 are reset
  351. //                Exit: sync_bit_1 and sync_bit_2 are set.
  352. //
  353. //        Called from: main()
  354. //
  355. // *******************************************************************
  356.                
  357. unsigned char find_sync()
  358.         {
  359.                 // colons OFF = no sync
  360.                 portb.5 = 0;        

  361.                 while ((sync_bit_1 && sync_bit_2) == 0)
  362.                         {
  363.                                 while(sample_flag == 0)
  364.                                         {
  365.                                                 ;        // wait for 32 samples/sec interrupt and get new sample
  366.                                         }
  367.                                 sample_flag = 0;

  368.                                 // Set up a counter which will count the number of agreements
  369.                                 // between the sample register and the sync pattern
  370.                                 sync_count = 0;

  371.                                 // XOR the sample register with the sync pattern to see which bits agree
  372.                                 sync_temp = sync ^ samples;

  373.                                 // Count the number of bit agreements between samples and initial sync pattern                        
  374.                                 for (i = 0; i < 32; i++)
  375.                                         {
  376.                                                 if (sync_temp.0 == 0)
  377.                                                         sync_count++;
  378.                                                 sync_temp >>= 1;
  379.                                         }
  380.                                 // compare agreement count to the sync_threshold value, set sync bit flags accordingly
  381.                                 if ((sync_count >= sync_threshold) && (sync_bit_1 == 0))
  382.                                         {
  383.                                                 sync_bit_1 = 1;

  384.                                         if (sync_bit_1 == 1)
  385.                                                 {
  386.                                                         for (j = 0; j < 32; j++)        // get 32 new samples
  387.                                                                 {
  388.                                                                         while(sample_flag == 0)
  389.                                                                                 {
  390.                                                                                         ;
  391.                                                                                 }
  392.                                                                         sample_flag = 0;
  393.                                                                 }
  394.                                                                
  395.                                                         sync_count = 0;
  396.                                                         sync_temp = sync ^ samples;        
  397.                                                         for (i = 0; i < 32; i++)
  398.                                                                 {
  399.                                                                         if (sync_temp.0 == 0)
  400.                                                                         sync_count++;
  401.                                                                         sync_temp >>= 1;
  402.                                                                 }
  403.                                                 
  404.                                                         if (sync_count >= sync_threshold)
  405.                                                 // sync found!!!
  406.                                                                 sync_bit_2 = 1;
  407.                                                         else
  408.                                                 // sync not found
  409.                                                                 sync_bit_1 = 0;
  410.                                                 }
  411.                                         }
  412.                         }        
  413.         }
  414. // ***************** end of find_sync *************************




  415. // ************************** get_bit() ***********************
  416. //
  417. //        this routine determines whether the received bit is a
  418. //        one or zero
  419. //
  420. //  Parameters:
  421. //        Entry:  none
  422. //        Exit: none
  423. //
  424. //        Called from: main()
  425. //
  426. // ***************************************************************

  427. void get_bit()
  428.         {
  429.                 unsigned char j;
  430.                 unsigned long one_temp;
  431.                 unsigned long zero_temp;

  432.                 for (j = 0; j < 32; j++)         // get 32 new samples
  433.                         {
  434.                                 while(sample_flag == 0)
  435.                                         {
  436.                                                 ;  // wait for sample time interrupt
  437.                                         }
  438.                                 sample_flag =0;
  439.                         }

  440.                 one_count = 0;
  441.                 zero_count = 0;
  442.                 one_temp = one ^ samples;
  443.                 zero_temp = zero ^ samples;        
  444.                 for (i = 0; i < 32; i++)
  445.                         {
  446.                                 if (one_temp.0 == 0)
  447.                                 one_count++;
  448.                                 one_temp >>= 1;
  449.                                                         
  450.                                 if (zero_temp.0 == 0)
  451.                                 zero_count++;
  452.                                 zero_temp >>= 1;
  453.                         }
  454.         }

  455. // ************* end of get_bit() **********************



  456. // *************** skip_bit() **************************
  457. //
  458. // this routine is used to skip over the wwvb reserved bits and
  459. // other bits not used for this clock design
  460. //
  461. // Parameters
  462. //        Entry: none
  463. //        Exit: none
  464. //
  465. //        Called from: main()
  466. //
  467. // *******************************************************

  468. void skip_bit()
  469.         {
  470.                 unsigned char j;

  471.                 for (j = 0; j < 32; j++)
  472.                         {
  473.                                 while(sample_flag == 0)
  474.                                         {
  475.                                                 ;    // wait for sample time interrupt
  476.                                         }
  477.                                 sample_flag = 0;
  478.                         }

  479.         }
  480. // ***************** end of skip_bit() **************************







  481. // *************************** main routine starts here *****************
  482. void main()
  483. {
  484.         // variable declarations
  485.         unsigned char k;
  486.         unsigned char temp_ten_minutes;
  487.         unsigned char temp_minutes;
  488.         unsigned char temp_hours;
  489.         unsigned char temp_ten_hours;        
  490.         unsigned char utc_hours;
  491.         unsigned char ten_utc_hours;
  492.         unsigned char a;
  493.         unsigned char x;
  494.         unsigned char y;
  495.         unsigned char z;

  496.         unsigned char last_msg_valid_flag = 0;
  497.         unsigned char dst = 0;        // daylight savings time flag.  1 = dst, 0 = std time

  498.         configure_mpu();
  499.         seconds = 0;
  500.         ten_seconds = 0;

  501.         //Endless loop
  502.         while( 1 )
  503.                 {
  504.                         sync_bit_1 = 0;
  505.                         sync_bit_2 = 0;

  506.                         find_sync();

  507.                         // sync found, process bits

  508.                         // seconds and ten_seconds reset here

  509.                         seconds_counter = 0;
  510.                         n = 31;

  511.                         wwv_minutes = 0;
  512.                         wwv_ten_minutes = 0;
  513.                         utc_hours = 0;
  514.                         ten_utc_hours = 0;
  515.                         wwv_hours = 0;
  516.                         wwv_ten_hours = 0;

  517.                         portb.5 = 1;  // colons ON = sync
  518.                         error = 0;
  519.                         // first get 3 bits of 10-minutes data (40, 20, 10, MSB first format)
  520.                         // the 4th bit is a reserved (don't care) bit
  521.                         for (k = 0; k < 3; k++)
  522.                                 {
  523.                                         get_bit();

  524.                                         if (one_count >= bit_threshold)
  525.                                                 {
  526.                                                         wwv_ten_minutes <<= 1;
  527.                                                         wwv_ten_minutes.0 = 1;
  528.                                                                 }
  529.                                         else
  530.                                                 if (zero_count >= bit_threshold)
  531.                                                         {
  532.                                                                 wwv_ten_minutes <<= 1;
  533.                                                                 wwv_ten_minutes.0 = 0;
  534.                                                         }
  535.                                                 else
  536.                                                         error = 1;  // handle error, did not detect 1 or 0 bit
  537.                                 }
  538. // ************ could add error check here to be sure ten-minutes are between 0 and 5 **********

  539.                         // skip over the don't care bit
  540.                         skip_bit();

  541.                         // first get 4 bits of minutes data (8, 4, 2, 1, MSB first format)
  542.                         if (error == 0)
  543.                                 {
  544.                                         for (k = 0; k < 4; k++)
  545.                                                 {
  546.                                                         get_bit();

  547.                                                         if (one_count >= bit_threshold)
  548.                                                                 {
  549.                                                                         wwv_minutes <<= 1;
  550.                                                                         wwv_minutes.0 = 1;
  551.                                                                 }
  552.                                                         else
  553.                                                                 if (zero_count >= bit_threshold)
  554.                                                                         {
  555.                                                                                 wwv_minutes <<= 1;
  556.                                                                                 wwv_minutes.0 = 0;
  557.                                                                         }
  558.                                                                 else
  559.                                                                         error = 1;  // handle error, did not detect 1 or 0 bit
  560.                                                 }
  561.                                 }
  562. // ************ could add error check here to be sure minutes are between 0 and 9 **********
  563.                                                 
  564.                                        
  565.                         // now get the next 2 bits representing 10 utc hour data (24-hour format)        
  566.                         if (error == 0)
  567.                                 {
  568.                                         // skip over the position marker and (2) reserved bits
  569.                                         for (k = 0; k < 3; k++)
  570.                                                 skip_bit();

  571.                                         for (k = 0; k < 2; k++)
  572.                                                 {
  573.                                                         get_bit();
  574.         
  575.                                                         if (one_count >= bit_threshold)
  576.                                                                 {
  577.                                                                         ten_utc_hours <<= 1;
  578.                                                                         ten_utc_hours.0 = 1;
  579.                                                                 }
  580.                                                         else
  581.                                                                 if (zero_count >= bit_threshold)
  582.                                                                         {
  583.                                                                                 ten_utc_hours <<= 1;
  584.                                                                                 ten_utc_hours.0 = 0;
  585.                                                                         }
  586.                                                                 else
  587.                                                                         error = 1; //handle error, did not detect 1 or 0 bit
  588.                                                 }
  589.                                 }
  590. // ************ could add error check here to be sure ten-utc_hours are between 0 and 2 **********


  591.                         // now get the 4 bits representing utc_hours
  592.                         if (error == 0)
  593.                                 {
  594.                                         // skip the next (reserved) bit
  595.                                         skip_bit();

  596.                                         for (k = 0; k < 4; k++)
  597.                                                 {
  598.                                                         get_bit();

  599.                                                         if (one_count >= bit_threshold)
  600.                                                                 {
  601.                                                                         utc_hours <<= 1;
  602.                                                                         utc_hours.0 = 1;
  603.                                                                 }
  604.                                                         else
  605.                                                                 if (zero_count >= bit_threshold)
  606.                                                                         {
  607.                                                                                 utc_hours <<= 1;
  608.                                                                                 utc_hours.0 = 0;
  609.                                                                         }
  610.                                                                 else
  611.                                                                         error = 1;  // handle error, did not detect 1 or 0 bit
  612.                                                 }
  613.                                 }


  614.                         // correct for time being valid at the previous frame sync marker
  615.                         if (error == 0)
  616.                                 {
  617.                                         temp_ten_minutes = wwv_ten_minutes;
  618.                                         x = 0;
  619.                                        
  620.                                         while ( temp_ten_minutes > 0)
  621.                                                 {
  622.                                                         x += 10;
  623.                                                         temp_ten_minutes--;
  624.                                                 }

  625.                                         y = x + wwv_minutes;                // y is now minutes in a single
  626.                                                                                                 // char format
  627.         
  628.                                         z = 0;                                                        
  629.                                         temp_ten_hours = ten_utc_hours;
  630.                                         while( temp_ten_hours > 0)
  631.                                                 {
  632.                                                         z += 10;
  633.                                                         temp_ten_hours--;
  634.                                                 }
  635.                                                 
  636.                                         a = z + utc_hours;                        // a is now hours in a single
  637.                                                                                                 // char format
  638.                                                                                                 
  639.                                         if (y < 59)
  640.                                                 y++;                                        // bump minutes
  641.                                         else                                                 // y = 59
  642.                                                 {
  643.                                                         y = 0;                                // bump hours
  644.                                                         if (a < 23)
  645.                                                                 a++;
  646.                                                         else
  647.                                                                 a = 0;
  648.                                                 }
  649.                                        
  650.                                         // now unpack back to 2-byte format
  651.                                         temp_ten_minutes = 0;

  652.                                         while (y > 9)
  653.                                                 {
  654.                                                         temp_ten_minutes++;
  655.                                                         y -= 10;
  656.                                                 }
  657.                                        
  658.                                         wwv_ten_minutes = temp_ten_minutes;
  659.                                         wwv_minutes = y;
  660.                                 
  661.                                         temp_ten_hours = 0;
  662.                                         while (a > 9)
  663.                                                 {
  664.                                                         temp_ten_hours++;
  665.                                                         a -= 10;
  666.                                                 }
  667.                                        
  668.                                         ten_utc_hours = temp_ten_hours;
  669.                                         utc_hours = a;
  670.                                 }

  671.                                 // daylight savings time info is in bits 57 and 58
  672.                                 // we will only test bit 57 for dst and do nothing for bit 58
  673.                                 // to allow re-sync

  674.                         if (error == 0)
  675.                                 {
  676.                                         // skip the next 38 bits to get to message bit 57
  677.                                         for (k = 0; k < 38; k++)
  678.                                                 skip_bit();
  679.                                                 
  680.                                         // get bit 57 to see if DST is in effect
  681.                                         get_bit();
  682.                                         if (one_count >= bit_threshold)
  683.                                                 dst = 1;
  684.                                         else
  685.                                                 if (zero_count >= bit_threshold)
  686.                                                         dst = 0;
  687.                                                 else
  688.                                                         error = 1; //handle error, did not detect 1 or 0 bit
  689.                                 }
  690.         
  691. // ************ could add error check here to be sure utc_hours are between 0 and 9 **********

  692.                         // ok, now we need to convert UTC hours to local (PST) time
  693.                         // ********** CHANGE THIS CODE SEGMENT FOR DIFFERENT TIME ZONES!!!!! *********
  694.                         if (error == 0)
  695.                                 {
  696.                                         temp_hours = 0;
  697.                                         for (k = 0; k < ten_utc_hours; k++)                                       
  698.                                                         temp_hours += 10;
  699.                                                                         
  700.                                         temp_hours = temp_hours + utc_hours;
  701.                                         // now have a single word representing utc hours
  702.                                                         
  703.                                         if (dst == 0)  // standard time
  704.                                                 {
  705.                                                         if (temp_hours <= 7)
  706.                                                                 local_hours = temp_hours + 16;
  707.                                                         if ((temp_hours > 7) && (temp_hours <= 23))
  708.                                                                 local_hours = temp_hours - 8;
  709.                                                 }
  710.                                         if (dst == 1)  // daylight savings time
  711.                                                 {
  712.                                                         if( temp_hours <= 6 )
  713.                                                                 local_hours = temp_hours + 17;
  714.                                                         if( (temp_hours > 6) && (temp_hours <= 23))
  715.                                                                 local_hours = temp_hours - 7;
  716.                                                 }

  717.                                         // if we made it this far with error = 0
  718.                                         // then the message is valid
  719.                                         msg_valid = 1;
  720.                                 }
  721.                         else
  722.                                 msg_valid = 0;
  723.         
  724.                 }  // end of while(1) endless loop
  725. }
复制代码


  零件清单

在零件清单中,我已经包括IC及零件,可能很难找到的制造商与Digi - Key库存数量。 电阻和电容,可以从众多的供应商购买的公用部分。
组件
零件编号
说明
制造商
  Digi - Key的股票#





  IC1的
的PIC 16F628
微控制器
  Microsemi的
  PIC16F628-04/P-ND
  IC2 - IC7
  4511N
  BCD到7段解码器/驱动器
各种
  296 - 3528 - 1 - ND
  IC8
  74HCT138
  3-8译码器
  各种
  296 - 1608 - 5 - ND
  IC9
  7805
  5V稳压器
  各种   LM7805CT - ND
  R1 - R42
  150欧姆1 / 8 W
电阻
  各种
  R43,R51
  10千欧姆1 / 8 W
电阻
  各种
  R44型 - 48
  270欧姆1 / 8 W
电阻
  各种
第一季度
为4 MHz
水晶
  各种   X971 - ND
  C1,C2,
  20 PF,50V
电容器
  各种
  C3,C4,C6
  0.1用友,50V
电容器
  各种
  C7
  10 uF的,35V
电容器
  各种
与天线接收模块
  CMMR - 6

  CMAX
  561 - 1014 - ND
  LED1 - LED6
  LDS - CA14RI
  1“LED 7段显示器
  Lumex公司
  67 - 1487 - ND

下载:
www.syyyd.com原理图.pdf (96.75 KB, 下载次数: 35)
clock5A C.rar (4.9 KB, 下载次数: 27)
clock5A HEX.zip (2.03 KB, 下载次数: 26)
PCBgerber_files.zip (58.1 KB, 下载次数: 27)


回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|手机版|联系我们|闽公网安备 35012102000020号|闽ICP备11020110号-1|圣源电子

GMT+8, 2024-9-20 00:27 , Processed in 0.049316 second(s), 21 queries .

Powered by Discuz! X3.4

© 2001-2017 Comsenz Inc.

快速回复 返回顶部 返回列表