I'm using a little header file to output some debug info to a logic analyzer. The macro's in that file unroll a statement such as DEBUG(23) into a bunch of sbi and cbi instructions which output that number in an async format. This way I can track which code is executed and when it's executed without changing the overall timing too much.
The problem is however that if the optimisation level is higher than -O1 the timing of the macro breaks.
Is there a way to group these sbi / cbi statements together so the optimiser won't touch them?
#ifdef DEBUG_PORT // Just to make sure the user knows the debug code is inserted. #warning Debug code inserted. // 3 little Macro's for internal use only. #define _SET (DEBUG_PORT |= DEBUG_BIT) #define _CLEAR (DEBUG_PORT &= ~DEBUG_BIT) #define _BIT(X,Y) ((X) &(0x01 << (Y)) ? (_SET) : (_CLEAR)) // Use this macro to enable the debug output pin. #define DEBUG_OUTPUT_ENABLE (DEBUG_DDR |= DEBUG_BIT) // Startbit, a bunch of data bits and a stop bit. #define DEBUG(X) (_CLEAR,\ _BIT(X,0), _BIT(X,1), _BIT(X,2),_BIT(X,3),\ _BIT(X,4), _BIT(X,5), _BIT(X,6), \ _SET) #else // Preprocessor removes debug statements. #define DEBUG_OUTPUT_ENABLE #define DEBUG(x) #endif
In this example below the debug bit stream is interrupted by the cpse and rjmp instructions because of optimisation.
ISR (USART_UDRE_vect) { // Uart Data Register Empty interrupt routine. // Sends the Next byte of A Packet to the UART. If the last bye is put in UDR // this interrupt disables itself and enables the transmission complete interrupt // to clean up. if(TxDBytes){ // if there's more data to be sent... DEBUG(0x37); UCSRB &= ~(1<<TXB8); // Send databytes from now on. // Bug: Can possibly be eliminated (do in MumarSend) UDR = *pTxd; // write next byte to data buffer. TxDBytes--; // A byte has been transmitted, so decrement... pTxd++; } else { DEBUG(0x38); UCSRB = (1<<RXEN)|(1<<TXEN)| // No change. (1<<TXCIE)| // Enable Transmission Complete, (0<<UDRIE)| // Disable UDRE interrupt. (1<<UCSZ2)|(0<<TXB8); // No change. } }
DEBUG(0x37); 3ba: a9 98 cbi 0x15, 1 ; 21 ISR (USART_UDRE_vect) { if(TxDBytes){ // if there's more data to be sent... 3bc: 81 11 cpse r24, r1 3be: 13 c0 rjmp .+38 ; 0x3e6 <__vector_12+0x42> UDR = *pTxd; // write next byte to data buffer. TxDBytes--; // A byte has been transmitted, so decrement... pTxd++; } else { DEBUG(0x38); 3c0: a9 98 cbi 0x15, 1 ; 21 3c2: a9 98 cbi 0x15, 1 ; 21 3c4: a9 98 cbi 0x15, 1 ; 21 3c6: a9 9a sbi 0x15, 1 ; 21 3c8: a9 9a sbi 0x15, 1 ; 21 3ca: a9 9a sbi 0x15, 1 ; 21 3cc: a9 98 cbi 0x15, 1 ; 21 3ce: a9 9a sbi 0x15, 1 ; 21