Sony's LANC camera control protocol project.
Dependencies: aconno_LANC aconno_bsp aconno_SEGGER_RTT
main.cpp@5:ecb7712b0825, 2017-11-01 (annotated)
- Committer:
- jurica238814
- Date:
- Wed Nov 01 17:39:50 2017 +0000
- Revision:
- 5:ecb7712b0825
- Parent:
- 4:6560e2966186
- Child:
- 6:8cf24e946b0b
Code refectoring done.
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
jurica238814 | 0:d616ca59aad8 | 1 | /* |
jurica238814 | 0:d616ca59aad8 | 2 | * Example to demonstrate usage of the nrf52's I2S interface |
jurica238814 | 0:d616ca59aad8 | 3 | * |
jurica238814 | 0:d616ca59aad8 | 4 | * Made by Jurica Resetar @ aconno |
jurica238814 | 0:d616ca59aad8 | 5 | * jurica_resetar@yahoo.com |
jurica238814 | 0:d616ca59aad8 | 6 | * More info @ aconno.de |
jurica238814 | 0:d616ca59aad8 | 7 | * |
jurica238814 | 0:d616ca59aad8 | 8 | * All rights reserved |
jurica238814 | 0:d616ca59aad8 | 9 | * |
jurica238814 | 0:d616ca59aad8 | 10 | */ |
jurica238814 | 0:d616ca59aad8 | 11 | |
jurica238814 | 0:d616ca59aad8 | 12 | #include "mbed.h" |
jurica238814 | 0:d616ca59aad8 | 13 | #include "acd52832_bsp.h" |
jurica238814 | 0:d616ca59aad8 | 14 | |
jurica238814 | 2:b28027b9c099 | 15 | #define MY_BUF_SIZE 13*8 |
jurica238814 | 1:3e3dded8192f | 16 | #define LANC_H 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF /* 13 B */ |
jurica238814 | 2:b28027b9c099 | 17 | #define LANC_H_L 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF /* 13 B */ |
jurica238814 | 1:3e3dded8192f | 18 | #define LANC_L 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 /* 13 B */ |
jurica238814 | 0:d616ca59aad8 | 19 | |
jurica238814 | 0:d616ca59aad8 | 20 | /* |
jurica238814 | 0:d616ca59aad8 | 21 | * Bitovi na I2S bus idu od MSBa do LSBa |
jurica238814 | 0:d616ca59aad8 | 22 | */ |
jurica238814 | 0:d616ca59aad8 | 23 | |
jurica238814 | 2:b28027b9c099 | 24 | #define LANC_COMMAND_PIN (p2) // Pin connected to Tr to pull lanc bus down/up 2/26 |
jurica238814 | 2:b28027b9c099 | 25 | #define LANC_PIN (p3) // Lanc bus pin (to scan for START/STOP bits) 3/25 |
jurica238814 | 5:ecb7712b0825 | 26 | #define LED_ON (0) |
jurica238814 | 5:ecb7712b0825 | 27 | #define LED_OFF (1) |
jurica238814 | 0:d616ca59aad8 | 28 | |
jurica238814 | 2:b28027b9c099 | 29 | DigitalOut alive(p24); |
jurica238814 | 2:b28027b9c099 | 30 | |
jurica238814 | 2:b28027b9c099 | 31 | uint8_t normalCommand[MY_BUF_SIZE] __attribute__ ((aligned (32))) = {LANC_L,LANC_L,LANC_L,LANC_H, LANC_H,LANC_L,LANC_L,LANC_L}; |
jurica238814 | 5:ecb7712b0825 | 32 | uint8_t zoomCommand[MY_BUF_SIZE] __attribute__ ((aligned (32))) = {LANC_L,LANC_L,LANC_L,LANC_H, LANC_L,LANC_H,LANC_L,LANC_L}; |
jurica238814 | 2:b28027b9c099 | 33 | uint8_t startStop[MY_BUF_SIZE] __attribute__ ((aligned (32))) = {LANC_H,LANC_H,LANC_L,LANC_L,LANC_H,LANC_H,LANC_L,LANC_L}; |
jurica238814 | 4:6560e2966186 | 34 | uint8_t zoomIn[MY_BUF_SIZE] __attribute__ ((aligned (32))) = {LANC_H,LANC_L,LANC_L,LANC_H,LANC_H,LANC_H,LANC_L,LANC_L}; // Tele |
jurica238814 | 4:6560e2966186 | 35 | uint8_t zoomOut[MY_BUF_SIZE] __attribute__ ((aligned (32))) = {LANC_H,LANC_H,LANC_L,LANC_H,LANC_H,LANC_H,LANC_L,LANC_L}; // Wide |
jurica238814 | 1:3e3dded8192f | 36 | |
jurica238814 | 5:ecb7712b0825 | 37 | uint32_t *normalCmdAddr = (uint32_t*)normalCommand; |
jurica238814 | 5:ecb7712b0825 | 38 | uint32_t *zoomCmdAddr = (uint32_t*)zoomCommand; |
jurica238814 | 5:ecb7712b0825 | 39 | uint32_t *startStopAddr = (uint32_t*)startStop; |
jurica238814 | 5:ecb7712b0825 | 40 | uint32_t *zoomInAddr = (uint32_t*)zoomIn; |
jurica238814 | 5:ecb7712b0825 | 41 | uint32_t *zoomOutAddr = (uint32_t*)zoomOut; |
jurica238814 | 2:b28027b9c099 | 42 | |
jurica238814 | 5:ecb7712b0825 | 43 | |
jurica238814 | 5:ecb7712b0825 | 44 | uint8_t volatile i2sFlag = 0; |
jurica238814 | 4:6560e2966186 | 45 | uint8_t state = 0; /* 1 -> Send command type, 0 -> send command */ |
jurica238814 | 1:3e3dded8192f | 46 | InterruptIn button(LANC_PIN); |
jurica238814 | 2:b28027b9c099 | 47 | Timer frameTimer; |
jurica238814 | 1:3e3dded8192f | 48 | |
jurica238814 | 5:ecb7712b0825 | 49 | void i2sReady(){ |
jurica238814 | 5:ecb7712b0825 | 50 | /* Interrupt handler */ |
jurica238814 | 5:ecb7712b0825 | 51 | i2sFlag = 1; |
jurica238814 | 5:ecb7712b0825 | 52 | } |
jurica238814 | 0:d616ca59aad8 | 53 | |
jurica238814 | 5:ecb7712b0825 | 54 | uint8_t waitForStartBit(){ |
jurica238814 | 5:ecb7712b0825 | 55 | static uint8_t firstInt = 1; |
jurica238814 | 3:eb5b87baf6cf | 56 | static int lastIntTime_us = 0; |
jurica238814 | 1:3e3dded8192f | 57 | |
jurica238814 | 5:ecb7712b0825 | 58 | while(!i2sFlag); // Wait for the interrupt to change the flag |
jurica238814 | 5:ecb7712b0825 | 59 | if(firstInt){ |
jurica238814 | 5:ecb7712b0825 | 60 | firstInt = 0; |
jurica238814 | 5:ecb7712b0825 | 61 | frameTimer.start(); |
jurica238814 | 5:ecb7712b0825 | 62 | } |
jurica238814 | 5:ecb7712b0825 | 63 | lastIntTime_us = frameTimer.read_us(); |
jurica238814 | 5:ecb7712b0825 | 64 | frameTimer.reset(); |
jurica238814 | 5:ecb7712b0825 | 65 | i2sFlag = 0; |
jurica238814 | 5:ecb7712b0825 | 66 | |
jurica238814 | 5:ecb7712b0825 | 67 | if(lastIntTime_us > 10000){ |
jurica238814 | 5:ecb7712b0825 | 68 | return 1; |
jurica238814 | 5:ecb7712b0825 | 69 | } |
jurica238814 | 5:ecb7712b0825 | 70 | else{ |
jurica238814 | 5:ecb7712b0825 | 71 | return 0; |
jurica238814 | 5:ecb7712b0825 | 72 | } |
jurica238814 | 5:ecb7712b0825 | 73 | } |
jurica238814 | 5:ecb7712b0825 | 74 | |
jurica238814 | 5:ecb7712b0825 | 75 | void sendi2sData(){ |
jurica238814 | 5:ecb7712b0825 | 76 | NRF_I2S->EVENTS_TXPTRUPD = 0; |
jurica238814 | 5:ecb7712b0825 | 77 | NRF_I2S->ENABLE = 1; |
jurica238814 | 5:ecb7712b0825 | 78 | NRF_I2S->TASKS_START = 1; |
jurica238814 | 5:ecb7712b0825 | 79 | |
jurica238814 | 5:ecb7712b0825 | 80 | while(!NRF_I2S->EVENTS_TXPTRUPD); // Wait for the data to be send |
jurica238814 | 5:ecb7712b0825 | 81 | NRF_I2S->EVENTS_TXPTRUPD = 0; |
jurica238814 | 5:ecb7712b0825 | 82 | while(!NRF_I2S->EVENTS_TXPTRUPD); // Wait for the data to be send |
jurica238814 | 5:ecb7712b0825 | 83 | NRF_I2S->EVENTS_TXPTRUPD = 0; |
jurica238814 | 5:ecb7712b0825 | 84 | NRF_I2S->TASKS_STOP = 1; |
jurica238814 | 5:ecb7712b0825 | 85 | while(!NRF_I2S->EVENTS_STOPPED); |
jurica238814 | 5:ecb7712b0825 | 86 | NRF_I2S->ENABLE = 0; |
jurica238814 | 5:ecb7712b0825 | 87 | } |
jurica238814 | 5:ecb7712b0825 | 88 | |
jurica238814 | 5:ecb7712b0825 | 89 | void sendCommand(uint32_t *commandType, uint32_t *command){ |
jurica238814 | 5:ecb7712b0825 | 90 | |
jurica238814 | 5:ecb7712b0825 | 91 | |
jurica238814 | 2:b28027b9c099 | 92 | /* |
jurica238814 | 2:b28027b9c099 | 93 | * Na prvi interrupt pokreni frameTimer. |
jurica238814 | 2:b28027b9c099 | 94 | * Na svaki interrupt (falling edge na Lanc busu) izmjeri vrijeme od zadnjeg eventa |
jurica238814 | 2:b28027b9c099 | 95 | * Ako je to vrijeme > 5ms, onda je upravo taj prekid izazvao start bit novog framea |
jurica238814 | 2:b28027b9c099 | 96 | * U tom slučaju, kreni s donjim kodom, inaće nemoj ništa slati |
jurica238814 | 2:b28027b9c099 | 97 | */ |
jurica238814 | 5:ecb7712b0825 | 98 | uint8_t cnt = 0; |
jurica238814 | 2:b28027b9c099 | 99 | |
jurica238814 | 5:ecb7712b0825 | 100 | for(cnt; cnt < 4; cnt++){ |
jurica238814 | 5:ecb7712b0825 | 101 | while(!(waitForStartBit())); |
jurica238814 | 5:ecb7712b0825 | 102 | NRF_I2S->TXD.PTR = (uint32_t)commandType; |
jurica238814 | 5:ecb7712b0825 | 103 | __disable_irq(); |
jurica238814 | 5:ecb7712b0825 | 104 | // First or second start bit |
jurica238814 | 5:ecb7712b0825 | 105 | wait_us(60); // Small delay for first bit after start bit |
jurica238814 | 5:ecb7712b0825 | 106 | sendi2sData(); |
jurica238814 | 5:ecb7712b0825 | 107 | __enable_irq(); |
jurica238814 | 5:ecb7712b0825 | 108 | i2sFlag = 0; |
jurica238814 | 2:b28027b9c099 | 109 | |
jurica238814 | 5:ecb7712b0825 | 110 | while(!i2sFlag); // Wait for new start bit (second byte into frame) |
jurica238814 | 2:b28027b9c099 | 111 | |
jurica238814 | 5:ecb7712b0825 | 112 | NRF_I2S->TXD.PTR = (uint32_t)command; |
jurica238814 | 5:ecb7712b0825 | 113 | __disable_irq(); |
jurica238814 | 5:ecb7712b0825 | 114 | // First or second start bit |
jurica238814 | 5:ecb7712b0825 | 115 | wait_us(60); // Small delay for first bit after start bit |
jurica238814 | 5:ecb7712b0825 | 116 | sendi2sData(); |
jurica238814 | 5:ecb7712b0825 | 117 | i2sFlag = 0; |
jurica238814 | 5:ecb7712b0825 | 118 | __enable_irq(); |
jurica238814 | 2:b28027b9c099 | 119 | } |
jurica238814 | 1:3e3dded8192f | 120 | } |
jurica238814 | 1:3e3dded8192f | 121 | |
jurica238814 | 5:ecb7712b0825 | 122 | void i2sInit(){ |
jurica238814 | 0:d616ca59aad8 | 123 | NRF_I2S->CONFIG.RXEN = 0; // Disable reception |
jurica238814 | 0:d616ca59aad8 | 124 | NRF_I2S->CONFIG.MCKEN = 1; // Enable MCK generator |
jurica238814 | 4:6560e2966186 | 125 | |
jurica238814 | 1:3e3dded8192f | 126 | NRF_I2S->CONFIG.MCKFREQ = 0x10000000; // DIV 31 |
jurica238814 | 1:3e3dded8192f | 127 | NRF_I2S->CONFIG.RATIO = 0; // Ratio = 32x |
jurica238814 | 0:d616ca59aad8 | 128 | |
jurica238814 | 1:3e3dded8192f | 129 | NRF_I2S->CONFIG.SWIDTH = 0; // Sample width = 8 bit |
jurica238814 | 1:3e3dded8192f | 130 | NRF_I2S->CONFIG.ALIGN = 0; // Alignment = Right |
jurica238814 | 0:d616ca59aad8 | 131 | NRF_I2S->CONFIG.FORMAT = 0; // Format = I2S |
jurica238814 | 0:d616ca59aad8 | 132 | NRF_I2S->CONFIG.CHANNELS = 0; // Use stereo |
jurica238814 | 0:d616ca59aad8 | 133 | |
jurica238814 | 1:3e3dded8192f | 134 | NRF_I2S->PSEL.LRCK = 27; // LRCK routed to pin 26 |
jurica238814 | 1:3e3dded8192f | 135 | NRF_I2S->PSEL.SDOUT = LANC_COMMAND_PIN; // SDOUT routed to pin 28 |
jurica238814 | 1:3e3dded8192f | 136 | NRF_I2S->PSEL.SCK = 30; // SCK routed to pin 30 |
jurica238814 | 1:3e3dded8192f | 137 | NRF_I2S->PSEL.MCK = 0x80000000; // MCK disconnected |
jurica238814 | 1:3e3dded8192f | 138 | NRF_I2S->PSEL.SDIN = 0x80000000; // SDIN disconnected |
jurica238814 | 0:d616ca59aad8 | 139 | |
jurica238814 | 2:b28027b9c099 | 140 | NRF_I2S->TXD.PTR = (uint32_t)normalCmdAddr; |
jurica238814 | 2:b28027b9c099 | 141 | NRF_I2S->RXTXD.MAXCNT = MY_BUF_SIZE/4; // Div with 4 cuz that's number of 32 bit words |
jurica238814 | 0:d616ca59aad8 | 142 | } |
jurica238814 | 0:d616ca59aad8 | 143 | |
jurica238814 | 0:d616ca59aad8 | 144 | |
jurica238814 | 5:ecb7712b0825 | 145 | int main(void){ |
jurica238814 | 5:ecb7712b0825 | 146 | alive = 0; |
jurica238814 | 5:ecb7712b0825 | 147 | |
jurica238814 | 5:ecb7712b0825 | 148 | i2sInit(); |
jurica238814 | 5:ecb7712b0825 | 149 | |
jurica238814 | 5:ecb7712b0825 | 150 | button.fall(i2sReady); |
jurica238814 | 5:ecb7712b0825 | 151 | |
jurica238814 | 5:ecb7712b0825 | 152 | while(1){ |
jurica238814 | 5:ecb7712b0825 | 153 | sendCommand(zoomCmdAddr, zoomInAddr); |
jurica238814 | 5:ecb7712b0825 | 154 | sendCommand(zoomCmdAddr, zoomInAddr); |
jurica238814 | 5:ecb7712b0825 | 155 | sendCommand(zoomCmdAddr, zoomInAddr); |
jurica238814 | 5:ecb7712b0825 | 156 | sendCommand(zoomCmdAddr, zoomInAddr); |
jurica238814 | 5:ecb7712b0825 | 157 | sendCommand(zoomCmdAddr, zoomInAddr); |
jurica238814 | 5:ecb7712b0825 | 158 | sendCommand(zoomCmdAddr, zoomInAddr); |
jurica238814 | 5:ecb7712b0825 | 159 | sendCommand(zoomCmdAddr, zoomInAddr); |
jurica238814 | 5:ecb7712b0825 | 160 | sendCommand(zoomCmdAddr, zoomInAddr); |
jurica238814 | 5:ecb7712b0825 | 161 | wait_ms(350); |
jurica238814 | 5:ecb7712b0825 | 162 | sendCommand(zoomCmdAddr, zoomOutAddr); |
jurica238814 | 5:ecb7712b0825 | 163 | sendCommand(zoomCmdAddr, zoomOutAddr); |
jurica238814 | 5:ecb7712b0825 | 164 | sendCommand(zoomCmdAddr, zoomOutAddr); |
jurica238814 | 5:ecb7712b0825 | 165 | sendCommand(zoomCmdAddr, zoomOutAddr); |
jurica238814 | 5:ecb7712b0825 | 166 | sendCommand(zoomCmdAddr, zoomOutAddr); |
jurica238814 | 5:ecb7712b0825 | 167 | sendCommand(zoomCmdAddr, zoomOutAddr); |
jurica238814 | 5:ecb7712b0825 | 168 | sendCommand(zoomCmdAddr, zoomOutAddr); |
jurica238814 | 5:ecb7712b0825 | 169 | sendCommand(zoomCmdAddr, zoomOutAddr); |
jurica238814 | 5:ecb7712b0825 | 170 | wait_ms(350); |
jurica238814 | 5:ecb7712b0825 | 171 | } |
jurica238814 | 5:ecb7712b0825 | 172 | } |