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

📄 spokepov.lss

📁 旋转16个LED灯控制程序
💻 LSS
📖 第 1 页 / 共 5 页
字号:
 5fe:	10 92 83 00 	sts	0x0083, r1
 602:	10 92 82 00 	sts	0x0082, r1
 606:	08 95       	ret

00000608 <main>:
}

int main(void) {
 608:	cf ed       	ldi	r28, 0xDF	; 223
 60a:	d0 e0       	ldi	r29, 0x00	; 0
 60c:	de bf       	out	0x3e, r29	; 62
 60e:	cd bf       	out	0x3d, r28	; 61

  uint8_t cmd;			// the reason we reset

  // MCUSR is the MCU Status Register (page 40).  It tells us
  // why we reset, and a reset is the only way to get here.
  
  cmd = MCUSR;
 610:	84 b7       	in	r24, 0x34	; 52
  
  // The first order of business is to tell the chip that
  // we've got things under control.
  
  MCUSR = 0;
 612:	14 be       	out	0x34, r1	; 52
  
  // Turn on watchdog timer immediately, this protects against
  // a 'stuck' system by resetting it.
  
  // WDTCSR is the Watchdog Timer Control Register (page 45).
  // We set it so that it'll generate a watchdog interrupt
  // every second.  The idea is that if things mess up,
  // the watchdog will kickstart us.
  
  WDTCSR = _BV(WDE) | _BV(WDP2) | _BV(WDP1); // 1 second
 614:	8e e0       	ldi	r24, 0x0E	; 14
 616:	81 bd       	out	0x21, r24	; 33
  
  // Initialize the various pins of the ATMEL, and set up
  // the interrupts.
  
  ioinit();
 618:	dc df       	rcall	.-72     	; 0x5d2 <ioinit>
  
  // Show that we are active.
  
  set_all(~0x01);
 61a:	8e ef       	ldi	r24, 0xFE	; 254
 61c:	0a de       	rcall	.-1004   	; 0x232 <set_all>

  // enable the interrupts.  I think this is not needed
  // since it'll immediately be done by the loop, below.
  
  sei();
 61e:	78 94       	sei
  
  // Loop until we timeout, at which point the ATMEL is
  // put to sleep.  If the communications routine timed
  // out, or the user pressed the button for >500ms,
  // then sensor_timer will be 0xFFFF and we'll immediately
  // sleep.
  
  // Change to for (;;) to see if it makes any difference
  
  for (;;) {
  
    // Reset the watchdog Timer.
    //
    // QUESTION: What's with toggling the PD0 output line here?
    // it doesn't seem to be connected to anything according to
    // the circuit diagram...
    
    // *** PORTD |= 0x1;
    asm("wdr");
 620:	a8 95       	wdr
    // *** PORTD &= ~0x1;

	// If the sensor_timer (incremented by TIMER0) maxes out
	// (in about 3 minutes), then sleep everything.
	
    if (sensor_timer.bytes.high_byte == 0xFF) {
 622:	80 91 83 00 	lds	r24, 0x0083
 626:	8f 3f       	cpi	r24, 0xFF	; 255
 628:	71 f4       	brne	.+28     	; 0x646 <main+0x3e>
      
      // Avoid pesky interruptions
      
      cli();
 62a:	f8 94       	cli
      
      // Turn off all LEDs - I guess LED 0 is one of the "invisible ones"
      
      set_all(0xFF);
 62c:	02 de       	rcall	.-1020   	; 0x232 <set_all>
      
      // Turn off power to the Hall Effect sensor.
      
      SENSOR_PORT &= ~_BV(SENSORPOWER);
 62e:	96 98       	cbi	0x12, 6	; 18
      
      // Deselect EEPROM
      
      SPIEE_CS_PORT |= _BV(SPIEE_CS);      // pull CS high to deselect
 630:	c4 9a       	sbi	0x18, 4	; 24
      
      // Turn off Watchdog (must be restarted when we get the wakeup)
      // Wakeup will be via the button interrupt.
      
      WDTCSR |= _BV(WDCE) | _BV(WDE);
 632:	81 b5       	in	r24, 0x21	; 33
 634:	88 61       	ori	r24, 0x18	; 24
 636:	81 bd       	out	0x21, r24	; 33
      WDTCSR = 0;
 638:	11 bc       	out	0x21, r1	; 33
      MCUCR |= _BV(SM1) | _BV(SM0) | _BV(SE);
 63a:	85 b7       	in	r24, 0x35	; 53
 63c:	80 67       	ori	r24, 0x70	; 112
 63e:	85 bf       	out	0x35, r24	; 53
      
      // Re-enable interrupts so we can get the wakeup!
      
      sei();
 640:	78 94       	sei
     
      // Go into sleep mode
      
      asm("sleep");
 642:	88 95       	sleep
 644:	ed cf       	rjmp	.-38     	; 0x620 <main+0x18>
      
    } else {
    
      // Do we have dynamic updating to do?
      
      #ifdef DYNAMIC
     
        uint8_t tBytes;						// Number of bytes to transfer
        
        // Use unions to overlay variables and save some space
        
        union {
          char *fPtr;						// from pointer
          var16bit divisor;					// the divisor for RPM
        } a;
        
        union {
          char *tPtr;						// to pointer
          char *divTable;					// divisor table
        } b;
        
        // Update the dynamic data display
        
        switch (dynamicType & 0xF0) {
 646:	80 91 7c 00 	lds	r24, 0x007C
 64a:	99 27       	eor	r25, r25
 64c:	80 7f       	andi	r24, 0xF0	; 240
 64e:	90 70       	andi	r25, 0x00	; 0
 650:	80 32       	cpi	r24, 0x20	; 32
 652:	91 05       	cpc	r25, r1
 654:	71 f0       	breq	.+28     	; 0x672 <main+0x6a>
 656:	81 32       	cpi	r24, 0x21	; 33
 658:	91 05       	cpc	r25, r1
 65a:	1c f4       	brge	.+6      	; 0x662 <main+0x5a>
 65c:	40 97       	sbiw	r24, 0x10	; 16
 65e:	29 f0       	breq	.+10     	; 0x66a <main+0x62>
 660:	6d c0       	rjmp	.+218    	; 0x73c <main+0x134>
 662:	c0 97       	sbiw	r24, 0x30	; 48
 664:	09 f4       	brne	.+2      	; 0x668 <main+0x60>
 666:	66 c0       	rjmp	.+204    	; 0x734 <main+0x12c>
 668:	69 c0       	rjmp	.+210    	; 0x73c <main+0x134>
           
          #ifdef DYNAMIC_REVCOUNT					// Rev counter compiled in?
            
            case 0x10:								// Rev counter
            
              tBytes = 4;							// number of bytes we'll move down below
 66a:	94 e0       	ldi	r25, 0x04	; 4
              a.fPtr = (char *)dynamicREV;
 66c:	c3 e7       	ldi	r28, 0x73	; 115
 66e:	d0 e0       	ldi	r29, 0x00	; 0
              break;                                // gets put into dynamicBuffer in reverse order.
 670:	66 c0       	rjmp	.+204    	; 0x73e <main+0x136>
            
          #endif
            
          #ifdef DYNAMIC_RPM						// RPM counter compiled in?
            
            case 0x20:
            
              // CODE NOT YET OPTIMIZED FOR SPACE.
              
              // Initialize the RPM counter to 0
              
              dynamicRPM[0]=dynamicRPM[1]=dynamicRPM[2] = '0';
 672:	80 e3       	ldi	r24, 0x30	; 48
 674:	80 93 72 00 	sts	0x0072, r24
 678:	80 91 72 00 	lds	r24, 0x0072
 67c:	80 93 71 00 	sts	0x0071, r24
 680:	80 91 71 00 	lds	r24, 0x0071
 684:	80 93 70 00 	sts	0x0070, r24
              
              // Get a copy of the TIMER1 value that we need to divide 732 by
              
              a.divisor.word = OCR1A;
 688:	ca b5       	in	r28, 0x2a	; 42
 68a:	db b5       	in	r29, 0x2b	; 43
              
              // Start out pointing to the SECOND element of the div732 array.
              // We need to set to the second one because the min value of the
              // OCR1A hibyte (max speed) is 01, and we'll do at most 7 shifts
              // before we see a bit.  But there are 8 bits after that that
              // might get looked at, so the div732 table must be 8 entries long.
              // We also add 2 so that we are pointing at the last byte of each
              // entry.
              
              b.divTable = (char *)(div732+5);				// 3 bytes per entry
 68c:	ab e2       	ldi	r26, 0x2B	; 43
 68e:	b0 e0       	ldi	r27, 0x00	; 0
              
              // Shift the divisor to the left and the divtable pointer to the
              // right until the high bit of the divisor is set
              
              while (a.divisor.bytes.high_byte < 0x80) {
               
                a.divisor.word = a.divisor.word << 1;
                b.divTable = b.divTable + 3;
 690:	d7 fd       	sbrc	r29, 7
 692:	04 c0       	rjmp	.+8      	; 0x69c <main+0x94>
 694:	cc 0f       	add	r28, r28
 696:	dd 1f       	adc	r29, r29
 698:	13 96       	adiw	r26, 0x03	; 3
 69a:	fa cf       	rjmp	.-12     	; 0x690 <main+0x88>
                 
              }
              
              // Once we have found the high bit, that tells us the fastest
              // the device could possibly be rotating.  Any other set bits in
              // a.divisor mean that the RPM is lower.  So what we do is clear
              // the high bit and add in our partial sums only when the bits
              // in the remainder are ** 0 **.  Since we just cleared the
              // high bit, it'll get counted.  If all the bits are zero, all
              // the sums will be added.
                    
              // NOTE: could be made smaller by using a.divisor.bytes.high_byte
              // below, sacrificing a bit of accuracy at very high speeds.
              
              a.divisor.word = a.divisor.word & 0x7FFF;
 69c:	df 77       	andi	r29, 0x7F	; 127
              
              while (b.divTable > div732) {
              
                if (a.divisor.bytes.high_byte < 0x80) {
                
                  // Add in the least significant bit.  Since the table is actual
                  // byte values, we don't need to deal with an ascii conversion
                
                  dynamicRPM[0] = dynamicRPM[0] + pgm_read_byte(b.divTable--);

                  if (dynamicRPM[0] > '9') {
                    dynamicRPM[0] = dynamicRPM[0] - 10;
                    dynamicRPM[1]++;
                  }
                
                  // repeat for second byte...
                
                  dynamicRPM[1] = dynamicRPM[1] + pgm_read_byte(b.divTable--);

                  if (dynamicRPM[1] > '9') {
                    dynamicRPM[1] = dynamicRPM[1] - 10;
                    dynamicRPM[2]++;
                  }
             
                  // and for third, but no carry needed this time
                
                  dynamicRPM[2] = dynamicRPM[2] + pgm_read_byte(b.divTable--);

				  // At this point, we've already subtracted 3 from b.divTable, so we're
				  // ready to go for the next loop.
				
				} else {
				
				  // But if we didn't add anything in, we need to shift b.divTable
				  
				  b.divTable = b.divTable - 3;
				  
				}
				
				// And finally move to the next bit
				
				a.divisor.word = a.divisor.word << 1;				
 69e:	80 e0       	ldi	r24, 0x00	; 0
 6a0:	a6 32       	cpi	r26, 0x26	; 38
 6a2:	b8 07       	cpc	r27, r24
 6a4:	09 f0       	breq	.+2      	; 0x6a8 <main+0xa0>
 6a6:	08 f4       	brcc	.+2      	; 0x6aa <main+0xa2>
 6a8:	41 c0       	rjmp	.+130    	; 0x72c <main+0x124>
 6aa:	d7 fd       	sbrc	r29, 7
 6ac:	3b c0       	rjmp	.+118    	; 0x724 <main+0x11c>
 6ae:	fb 2f       	mov	r31, r27
 6b0:	ea 2f       	mov	r30, r26
 6b2:	11 97       	sbiw	r26, 0x01	; 1
 6b4:	c8 95       	lpm
 6b6:	90 2d       	mov	r25, r0
 6b8:	80 91 70 00 	lds	r24, 0x0070
 6bc:	89 0f       	add	r24, r25
 6be:	80 93 70 00 	sts	0x0070, r24
 6c2:	80 91 70 00 	lds	r24, 0x0070
 6c6:	8a 33       	cpi	r24, 0x3A	; 58
 6c8:	50 f0       	brcs	.+20     	; 0x6de <main+0xd6>
 6ca:	80 91 70 00 	lds	r24, 0x0070
 6ce:	8a 50       	subi	r24, 0x0A	; 10
 6d0:	80 93 70 00 	sts	0x0070, r24
 6d4:	80 91 71 00 	lds	r24, 0x0071
 6d8:	8f 5f       	subi	r24, 0xFF	; 255
 6da:	80 93 71 00 	sts	0x0071, r24
 6de:	fb 2f       	mov	r31, r27
 6e0:	ea 2f       	mov	r30, r26
 6e2:	11 97       	sbiw	r26, 0x01	; 1
 6e4:	c8 95       	lpm
 6e6:	90 2d       	mov	r25, r0
 6e8:	80 91 71 00 	lds	r24, 0x0071
 6ec:	89 0f       	add	r24, r25
 6ee:	80 93 71 00 	sts	0x0071, r24
 6f2:	80 91 71 00 	lds	r24, 0x0071
 6f6:	8a 33       	cpi	r24, 0x3A	; 58
 6f8:	50 f0       	brcs	.+20     	; 0x70e <main+0x106>
 6fa:	80 91 71 00 	lds	r24, 0x0071
 6fe:	8a 50       	subi	r24, 0x0A	; 10
 700:	80 93 71 00 	sts	0x0071, r24
 704:	80 91 72 00 	lds	r24, 0x0072
 708:	8f 5f       	subi	r24, 0xFF	; 255
 70a:	80 93 72 00 	sts	0x0072, r24
 70e:	fb 2f       	mov	r31, r27
 710:	ea 2f       	mov	r30, r26
 712:	11 97       	sbiw	r26, 0x01	; 1
 714:	c8 95       	lpm
 716:	90 2d       	mov	r25, r0
 718:	80 91 72 00 	lds	r24, 0x0072
 71c:	89 0f       	add	r24, r25
 71e:	80 93 72 00 	sts	0x0072, r24
 722:	01 c0       	rjmp	.+2      	; 0x726 <main+0x11e>
 724:	13 97       	sbiw	r26, 0x03	; 3
 726:	cc 0f       	add	r28, r28
 728:	dd 1f       	adc	r29, r29
 72a:	b9 cf       	rjmp	.-142    	; 0x69e <main+0x96>
								
			  }
			  
			  // And when that's all done, we just set up for the move
			  
			  tBytes = 3;
 72c:	93 e0       	ldi	r25, 0x03	; 3
			  a.fPtr = (char *)dynamicRPM;
 72e:	c0 e7       	ldi	r28, 0x70	; 112
 730:	d0 e0       	ldi	r29, 0x00	; 0
              
              break;
 732:	05 c0       	rjmp	.+10     	; 0x73e <main+0x136>
              
          #endif
            
          #ifdef DYNAMIC_TIME						// Clock compiled in?
            
            case 0x30:								// Rev counter
            
              tBytes = 8;							// number of bytes we'll move down below
 734:	98 e0       	ldi	r25, 0x08	; 8
              a.fPtr = (char *)dynamicTime;
 736:	c8 e6       	ldi	r28, 0x68	; 104
 738:	d0 e0       	ldi	r29, 0x00	; 0
              break;                                // gets put into dynamicBuffer in reverse order.
 73a:	01 c0       	rjmp	.+2      	; 0x73e <main+0x136>
            
          #endif
            
          default:								// This will get executed if no dynamic data
            tBytes = 0x00;						// and will clear things.
 73c:	90 e0       	ldi	r25, 0x00	; 0
               
        }
          
        // If we have bytes to transfer, and if the dynamic display
        // is still active, then transfer the bytes into the display
           
        cli();
 73e:	f8 94       	cli
           
        if ( (dynamicType != 0x00) && (tBytes != 0x00) ) {
 740:	80 91 7c 00 	lds	r24, 0x007C
 744:	88 23       	and	r24, r24
 746:	59 f0       	breq	.+22     	; 0x75e <main+0x156>
 748:	99 23       	and	r25, r25
 74a:	49 f0       	breq	.+18     	; 0x75e <main+0x156>
           
          b.tPtr = (char *)dynamicPtr;			// we now know dynamicPtr is valid
 74c:	a0 91 7d 00

⌨️ 快捷键说明

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