Mercurial > hg > beaglert
comparison pru_rtaudio.p @ 38:a9af130097e8 staging
GPIO pins are initialised as inputs by ARM to avoid spikes at startup, through gpio_set_dir. The buffers are set to 0x000ffff during initialisation. LastDigitalBuffer is
initialized to 0x0000ffff.
author | Giulio Moro <giuliomoro@yahoo.it> |
---|---|
date | Tue, 12 May 2015 23:48:37 +0100 |
parents | 6d64ee8c0754 |
children | 638bc1ae2500 |
comparison
equal
deleted
inserted
replaced
35:46571f8f04a1 | 38:a9af130097e8 |
---|---|
180 // Flags for the flags register | 180 // Flags for the flags register |
181 #define FLAG_BIT_BUFFER1 0 | 181 #define FLAG_BIT_BUFFER1 0 |
182 #define FLAG_BIT_USE_SPI 1 | 182 #define FLAG_BIT_USE_SPI 1 |
183 #define FLAG_BIT_MCASP_HWORD 2 // Whether we are on the high word for McASP transmission | 183 #define FLAG_BIT_MCASP_HWORD 2 // Whether we are on the high word for McASP transmission |
184 #define FLAG_BIT_USE_DIGITAL 3 | 184 #define FLAG_BIT_USE_DIGITAL 3 |
185 /*#define FLAG_BIT_DIGITAL_BUFFER 4 //Whether we are using buffer located at | |
186 // 0: MEM_DIGITAL_BASE or | |
187 */ // 1: MEM_DIGITAL_BASE + 512 | |
188 // Registers used throughout | 185 // Registers used throughout |
189 | 186 |
190 // r1, r2, r3 are used for temporary storage | 187 // r1, r2, r3 are used for temporary storage |
191 #define MEM_DIGITAL_BASE 0x11000 //Base address for DIGITAL : Shared RAM + 0x400 | 188 #define MEM_DIGITAL_BASE 0x11000 //Base address for DIGITAL : Shared RAM + 0x400 |
192 #define MEM_DIGITAL_BUFFER1_OFFSET 0x400 //Start pointer to DIGITAL_BUFFER1, which is 256 words after. | 189 #define MEM_DIGITAL_BUFFER1_OFFSET 0x400 //Start pointer to DIGITAL_BUFFER1, which is 256 words after. |
412 //regardless of whether the order is gpio1-gpio2 or gpio2-gpio1 | 409 //regardless of whether the order is gpio1-gpio2 or gpio2-gpio1 |
413 JMP r28.w0 // go back to ADC_WRITE_GPIO | 410 JMP r28.w0 // go back to ADC_WRITE_GPIO |
414 | 411 |
415 // DIGITAL new code ends here | 412 // DIGITAL new code ends here |
416 | 413 |
417 | 414 |
415 .macro HANG | |
416 DALOOP: | |
417 set r30.t14 | |
418 clr r30.t14 | |
419 QBA DALOOP | |
420 .endm | |
418 // Bring CS line low to write to DAC | 421 // Bring CS line low to write to DAC |
419 .macro DAC_CS_ASSERT | 422 .macro DAC_CS_ASSERT |
420 MOV r27, DAC_CS_PIN | 423 MOV r27, DAC_CS_PIN |
421 MOV r28, DAC_GPIO + GPIO_CLEARDATAOUT | 424 MOV r28, DAC_GPIO + GPIO_CLEARDATAOUT |
422 SBBO r27, r28, 0, 4 | 425 SBBO r27, r28, 0, 4 |
595 // Default number of channels in case SPI disabled | 598 // Default number of channels in case SPI disabled |
596 LDI reg_num_channels, 8 | 599 LDI reg_num_channels, 8 |
597 | 600 |
598 // Find out whether we should use DIGITAL | 601 // Find out whether we should use DIGITAL |
599 LBBO r2, reg_comm_addr, COMM_USE_DIGITAL, 4 | 602 LBBO r2, reg_comm_addr, COMM_USE_DIGITAL, 4 |
600 QBEQ DIGITAL_FLAG_CHECK_DONE, r2, 0 | 603 QBEQ DIGITAL_INIT_DONE, r2, 0 // if we use digital |
601 SET reg_flags, reg_flags, FLAG_BIT_USE_DIGITAL | 604 SET reg_flags, reg_flags, FLAG_BIT_USE_DIGITAL |
602 // SET reg_flags, reg_flags, FLAG_BIT_DIGITAL_BUFFER //set the flag, so that in WRITE_ONE_BUFFER we will start from buffer0 | 605 /* This block of code is not really needed, as the memory is initialized by ARM before the PRU is started. |
603 DIGITAL_FLAG_CHECK_DONE: | 606 Will leave it here for future reference |
607 DIGITAL_INIT: //set the digital buffer to 0x0000ffff (all inputs), to prevent unwanted high outputs | |
608 //the loop is unrolled by a factor of four just to take advantage of the speed of SBBO on larger byte bursts, but there is no real need for it | |
609 MOV r2, 0x0000ffff //value to store. 0x0000ffff means all inputs | |
610 MOV r3, MEM_DIGITAL_BASE //start of the digital buffer | |
611 MOV r4, MEM_DIGITAL_BASE+2*MEM_DIGITAL_BUFFER1_OFFSET //end of the digital buffer | |
612 DIGITAL_INIT_BUFFER_LOOP: | |
613 SBBO r2, r3, 0, 4 | |
614 ADD r3, r3, 4 //increment pointer | |
615 QBGT DIGITAL_INIT_BUFFER_LOOP, r3, r4 //loop until we reach the end of the buffer | |
616 */ | |
617 DIGITAL_INIT_DONE: | |
604 // Find out whether we should use SPI ADC and DAC | 618 // Find out whether we should use SPI ADC and DAC |
605 LBBO r2, reg_comm_addr, COMM_USE_SPI, 4 | 619 LBBO r2, reg_comm_addr, COMM_USE_SPI, 4 |
606 QBEQ SPI_FLAG_CHECK_DONE, r2, 0 | 620 QBEQ SPI_FLAG_CHECK_DONE, r2, 0 |
607 SET reg_flags, reg_flags, FLAG_BIT_USE_SPI | 621 SET reg_flags, reg_flags, FLAG_BIT_USE_SPI |
608 | |
609 SPI_FLAG_CHECK_DONE: | 622 SPI_FLAG_CHECK_DONE: |
610 // If we don't use SPI, then skip all this init | 623 // If we don't use SPI, then skip all this init |
611 QBBC SPI_INIT_DONE, reg_flags, FLAG_BIT_USE_SPI | 624 QBBC SPI_INIT_DONE, reg_flags, FLAG_BIT_USE_SPI |
612 | 625 |
613 // Load the number of channels: valid values are 8, 4 or 2 | 626 // Load the number of channels: valid values are 8, 4 or 2 |
747 | 760 |
748 MCASP_REG_SET_BIT_AND_POLL MCASP_RGBLCTL, (1 << 4) // Set RFRST | 761 MCASP_REG_SET_BIT_AND_POLL MCASP_RGBLCTL, (1 << 4) // Set RFRST |
749 MCASP_REG_SET_BIT_AND_POLL MCASP_XGBLCTL, (1 << 12) // Set XFRST | 762 MCASP_REG_SET_BIT_AND_POLL MCASP_XGBLCTL, (1 << 12) // Set XFRST |
750 | 763 |
751 // Initialisation | 764 // Initialisation |
752 LBBO reg_frame_total, reg_comm_addr, COMM_BUFFER_FRAMES, 4 // Total frame count (SPI; 0.5x-2x for McASP) | 765 LBBO reg_frame_total, reg_comm_addr, COMM_BUFFER_FRAMES, 4 // Total frame count (SPI; 0.5x-2x for McASP) |
753 MOV reg_dac_buf0, 0 // DAC buffer 0 start pointer | 766 MOV reg_dac_buf0, 0 // DAC buffer 0 start pointer |
754 LSL reg_dac_buf1, reg_frame_total, 1 // DAC buffer 1 start pointer = N[ch]*2[bytes]*bufsize | 767 LSL reg_dac_buf1, reg_frame_total, 1 // DAC buffer 1 start pointer = N[ch]*2[bytes]*bufsize |
755 LMBD r2, reg_num_channels, 1 // Returns 1, 2 or 3 depending on the number of channels | 768 LMBD r2, reg_num_channels, 1 // Returns 1, 2 or 3 depending on the number of channels |
756 LSL reg_dac_buf1, reg_dac_buf1, r2 // Multiply by 2, 4 or 8 to get the N[ch] scaling above | 769 LSL reg_dac_buf1, reg_dac_buf1, r2 // Multiply by 2, 4 or 8 to get the N[ch] scaling above |
757 MOV reg_mcasp_buf0, 0 // McASP DAC buffer 0 start pointer | 770 MOV reg_mcasp_buf0, 0 // McASP DAC buffer 0 start pointer |
758 LSL reg_mcasp_buf1, reg_frame_total, r2 // McASP DAC buffer 1 start pointer = 2[ch]*2[bytes]*(N/4)[samples/spi]*bufsize | 771 LSL reg_mcasp_buf1, reg_frame_total, r2 // McASP DAC buffer 1 start pointer = 2[ch]*2[bytes]*(N/4)[samples/spi]*bufsize |
759 CLR reg_flags, reg_flags, FLAG_BIT_BUFFER1 // Bit 0 holds which buffer we are on | 772 CLR reg_flags, reg_flags, FLAG_BIT_BUFFER1 // Bit 0 holds which buffer we are on |
760 MOV r2, 0 | 773 MOV r2, 0 |
761 SBBO r2, reg_comm_addr, COMM_FRAME_COUNT, 4 // Start with frame count of 0 | 774 SBBO r2, reg_comm_addr, COMM_FRAME_COUNT, 4 // Start with frame count of 0 |
762 | 775 /* This block of code is not really needed, as the memory is initialized by ARM before the PRU is started. |
776 Will leave it here for future reference | |
777 //Initialise all SPI and audio buffers (DAC0, DAC1, ADC0, ADC1) to zero. | |
778 //This is useful for analog outs so they do not have spikes during the first buffer. | |
779 //This is not very useful for audio, as you still hear the initial "tumpf" when the converter starts | |
780 //and each sample in the DAC buffer is reset to 0 after it is written to the DAC. | |
781 | |
782 QBBC SPI_INIT_BUFFER_DONE, reg_flags, FLAG_BIT_USE_SPI | |
783 //Initialize SPI buffers | |
784 //compute the memory offset of the end of the audio buffer and store it in r4 | |
785 SUB r4, reg_dac_buf1, reg_dac_buf0 // length of the buffer, assumes reg_dac_buf1>ref_dac_buf0 | |
786 LSL r4, r4, 2 //length of four buffers (DAC0, DAC1, ADC0, ADC1) | |
787 ADD r4, reg_dac_buf0, r4 //total offset | |
788 MOV r2, 0// value to store | |
789 MOV r3, 0 // offset counter | |
790 SPI_INIT_BUFFER_LOOP: | |
791 SBCO r2, C_ADC_DAC_MEM, r3, 4 | |
792 ADD r3, r3, 4 | |
793 QBGT SPI_INIT_BUFFER_LOOP, r3, r4 | |
794 SPI_INIT_BUFFER_DONE: | |
795 | |
796 //Initialize audio buffers | |
797 //compute the memory offset of the end of the audio buffer and store it in r4 | |
798 SUB r4, reg_mcasp_buf1, reg_mcasp_buf0 // length of the buffer, assumes reg_mcasp_buf1>ref_mcasp_buf0 | |
799 LSL r4, r4, 2 //length of four buffers (DAC0, DAC1, ADC0, ADC1) | |
800 ADD r4, reg_mcasp_buf0, r4 //total offset | |
801 MOV r2, 0 // value to store | |
802 MOV r3, 0 // offset counter | |
803 MCASP_INIT_BUFFER_LOOP: | |
804 SBCO r2, C_MCASP_MEM, r3, 4 | |
805 ADD r3, r3, 4 | |
806 QBGT MCASP_INIT_BUFFER_LOOP, r3, r4 | |
807 */ | |
763 // Here we are out of sync by one TDM slot since the 0 word transmitted above will have occupied | 808 // Here we are out of sync by one TDM slot since the 0 word transmitted above will have occupied |
764 // the first output slot. Send one more word before jumping into the loop. | 809 // the first output slot. Send one more word before jumping into the loop. |
765 MCASP_DAC_WAIT_BEFORE_LOOP: | 810 MCASP_DAC_WAIT_BEFORE_LOOP: |
766 LBBO r2, reg_mcasp_addr, MCASP_XSTAT, 4 | 811 LBBO r2, reg_mcasp_addr, MCASP_XSTAT, 4 |
767 QBBC MCASP_DAC_WAIT_BEFORE_LOOP, r2, MCASP_XSTAT_XDATA_BIT | 812 QBBC MCASP_DAC_WAIT_BEFORE_LOOP, r2, MCASP_XSTAT_XDATA_BIT |
776 QBBC MCASP_ADC_WAIT_BEFORE_LOOP, r2, MCASP_RSTAT_RDATA_BIT | 821 QBBC MCASP_ADC_WAIT_BEFORE_LOOP, r2, MCASP_RSTAT_RDATA_BIT |
777 | 822 |
778 MCASP_REG_READ_EXT MCASP_RBUF, r2 | 823 MCASP_REG_READ_EXT MCASP_RBUF, r2 |
779 | 824 |
780 WRITE_ONE_BUFFER: | 825 WRITE_ONE_BUFFER: |
826 | |
781 // Write a single buffer of DAC samples and read a buffer of ADC samples | 827 // Write a single buffer of DAC samples and read a buffer of ADC samples |
782 // Load starting positions | 828 // Load starting positions |
783 MOV reg_dac_current, reg_dac_buf0 // DAC: reg_dac_current is current pointer | 829 MOV reg_dac_current, reg_dac_buf0 // DAC: reg_dac_current is current pointer |
784 LMBD r2, reg_num_channels, 1 // 1, 2 or 3 for 2, 4 or 8 channels | 830 LMBD r2, reg_num_channels, 1 // 1, 2 or 3 for 2, 4 or 8 channels |
785 LSL reg_adc_current, reg_frame_total, r2 | 831 LSL reg_adc_current, reg_frame_total, r2 |
790 LSL reg_mcasp_adc_current, reg_mcasp_adc_current, 1 | 836 LSL reg_mcasp_adc_current, reg_mcasp_adc_current, 1 |
791 ADC reg_mcasp_adc_current, reg_mcasp_adc_current, reg_mcasp_dac_current | 837 ADC reg_mcasp_adc_current, reg_mcasp_adc_current, reg_mcasp_dac_current |
792 MOV reg_frame_current, 0 | 838 MOV reg_frame_current, 0 |
793 QBBS DIGITAL_BASE_CHECK_SET, reg_flags, FLAG_BIT_BUFFER1 //check which buffer we are using for DIGITAL | 839 QBBS DIGITAL_BASE_CHECK_SET, reg_flags, FLAG_BIT_BUFFER1 //check which buffer we are using for DIGITAL |
794 // if we are here, we are using buffer0 | 840 // if we are here, we are using buffer0 |
795 MOV r2, 0 //so adjust offset appropriately | 841 MOV reg_digital_current, MEM_DIGITAL_BASE |
796 QBA DIGITAL_BASE_CHECK_DONE | 842 QBA DIGITAL_BASE_CHECK_DONE |
797 DIGITAL_BASE_CHECK_SET: //if we are here, we are using buffer1 | 843 DIGITAL_BASE_CHECK_SET: //if we are here, we are using buffer1 |
798 MOV r2, MEM_DIGITAL_BUFFER1_OFFSET //so adjust offset appropriately | 844 MOV reg_digital_current, MEM_DIGITAL_BASE+MEM_DIGITAL_BUFFER1_OFFSET //so adjust offset appropriately |
799 DIGITAL_BASE_CHECK_DONE: | 845 DIGITAL_BASE_CHECK_DONE: |
800 MOV reg_digital_current, MEM_DIGITAL_BASE | |
801 ADD reg_digital_current, reg_digital_current, r2 | |
802 | 846 |
803 WRITE_LOOP: | 847 WRITE_LOOP: |
804 // Write N channels to DAC from successive values in memory | 848 // Write N channels to DAC from successive values in memory |
805 // At the same time, read N channels from ADC | 849 // At the same time, read N channels from ADC |
806 // Unrolled by a factor of 2 to get high and low words | 850 // Unrolled by a factor of 2 to get high and low words |
897 SUB r7, reg_num_channels, 1 | 941 SUB r7, reg_num_channels, 1 |
898 AND r8, r8, r7 | 942 AND r8, r8, r7 |
899 LSL r8, r8, AD7699_CHANNEL_OFFSET | 943 LSL r8, r8, AD7699_CHANNEL_OFFSET |
900 MOV r7, AD7699_CFG_MASK | 944 MOV r7, AD7699_CFG_MASK |
901 OR r7, r7, r8 | 945 OR r7, r7, r8 |
946 | |
902 //ssssssssssssssssssssssssssss | 947 //ssssssssssssssssssssssssssss |
903 ADC_WRITE_GPIO r7, r7, r1 | 948 ADC_WRITE_GPIO r7, r7, r1 |
904 | 949 |
905 // Mask out only the relevant 16 bits and store in reg_adc_data | 950 // Mask out only the relevant 16 bits and store in reg_adc_data |
906 MOV r2, 0xFFFF | 951 MOV r2, 0xFFFF |