Subversion Repositories svn.mios32

Rev

Rev 1214 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
1214 tk 1
// $Id: app.c 2425 2016-11-03 00:44:22Z tk $
2
/*
3
 * SRIO Fast Scan (10 uS)
4
 *
5
 * ==========================================================================
6
 *
7
 *  Copyright (C) <year> <your name> (<your email address>)
8
 *  Licensed for personal non-commercial use only.
9
 *  All other rights reserved.
10
 *
11
 * ==========================================================================
12
 */
13
 
14
/////////////////////////////////////////////////////////////////////////////
15
// Include files
16
/////////////////////////////////////////////////////////////////////////////
17
 
18
#include <mios32.h>
19
#include "app.h"
20
 
21
// include everything FreeRTOS related we don't understand yet ;)
22
#include <FreeRTOS.h>
23
#include <portmacro.h>
24
#include <task.h>
25
#include <queue.h>
26
#include <semphr.h>
27
 
28
 
29
// define priority level for DIN task:
30
// use lower priority as MIOS32 specific tasks (3)
31
// so that the task can run endless
32
#define PRIORITY_TASK_DIN_HANDLER   ( tskIDLE_PRIORITY + 1 )
33
 
34
// local prototype of the task function
35
static void TASK_DIN_Handler(void *pvParameters);
36
 
37
 
38
/////////////////////////////////////////////////////////////////////////////
39
// Local Prototypes
40
/////////////////////////////////////////////////////////////////////////////
41
 
42
static void SRIO_Handler(void);
43
 
44
 
45
/////////////////////////////////////////////////////////////////////////////
46
// Local Variables
47
/////////////////////////////////////////////////////////////////////////////
48
 
49
static u8 muxctr;       //JM counter for mux pointer
50
 
51
static volatile u8 srio_dout[4][MIOS32_SRIO_NUM_SR];    //jm add 2d to dout array
52
static volatile u8 srio_din[4][MIOS32_SRIO_NUM_SR];
53
static volatile u8 srio_din_buffer[4][MIOS32_SRIO_NUM_SR];
54
static volatile u8 srio_din_changed[4][MIOS32_SRIO_NUM_SR];
55
 
56
 
57
 
58
/////////////////////////////////////////////////////////////////////////////
59
// This hook is called after startup to initialize the application
60
/////////////////////////////////////////////////////////////////////////////
61
void APP_Init(void)
62
{
63
  // initialize all LEDs
64
  MIOS32_BOARD_LED_Init(0xffffffff);
65
 
66
  // initialize some pins of J5A/J5B/J5C as outputs in Push-Pull Mode - JM
67
  int pin;
68
  for(pin=0; pin<9; ++pin)
69
    MIOS32_BOARD_J5_PinInit(pin, MIOS32_BOARD_PIN_MODE_OUTPUT_PP);
70
 
71
  // Pin 11 as input with pull-up enabled
72
  MIOS32_BOARD_J5_PinInit(11, MIOS32_BOARD_PIN_MODE_INPUT_PU);  
73
 
74
  // clear chains
75
  // will be done again in MIOS32_DIN_Init and MIOS32_DOUT_Init
76
  // we don't reference to these functions here to allow the programmer to remove/replace these driver modules)
77
  // MIOS32_BOARD_J5_PinSet(3, 1);  //jm
78
  int i, j;
79
  for(j=0; j<4; ++j) {
80
    for(i=0; i<MIOS32_SRIO_NUM_SR; ++i) {
81
      srio_dout[j][i] = 0x00;   // passive state (LEDs off) JM todo:add all dim levels?
82
      srio_din[j][i] = 0xff;            // passive state (Buttons depressed) JM
83
      srio_din_buffer[j][i] = 0xff;     // passive state (Buttons depressed) JM
84
      srio_din_changed[j][i] = 0;       // no change JM
85
    }
86
  }
87
 
88
  // initial state of RCLK
89
  MIOS32_SPI_RC_PinSet(MIOS32_SRIO_SPI, MIOS32_SRIO_SPI_RC_PIN, 1); // spi, rc_pin, pin_value
90
 
91
  // init GPIO structure
92
  // use Push-Pull with strong (!) drivers
93
  MIOS32_SPI_IO_Init(MIOS32_SRIO_SPI, MIOS32_SPI_PIN_DRIVER_STRONG);
94
 
95
  // init SPI port for baudrate of ca. 2 uS period @ 72 MHz
96
  MIOS32_SPI_TransferModeInit(MIOS32_SRIO_SPI, MIOS32_SPI_MODE_CLK1_PHASE1, MIOS32_SPI_PRESCALER_4); //org=128 JM
97
 
98
  // start first DMA transfer (takes 5us)
99
  MIOS32_SPI_TransferBlock(MIOS32_SRIO_SPI,
100
               (u8 *)&srio_dout[muxctr][0], (u8 *)&srio_din_buffer[muxctr][0],  //jm todo ??
101
               MIOS32_SRIO_NUM_SR,
102
               SRIO_Handler);
103
 
104
  // start task
2425 tk 105
  xTaskCreate(TASK_DIN_Handler, "DIN_Handler", configMINIMAL_STACK_SIZE, NULL, PRIORITY_TASK_DIN_HANDLER, NULL);
1214 tk 106
 
107
}
108
 
109
 
110
/////////////////////////////////////////////////////////////////////////////
111
// This task is running endless in background
112
/////////////////////////////////////////////////////////////////////////////
113
void APP_Background(void)
114
{
115
}
116
 
117
 
118
/////////////////////////////////////////////////////////////////////////////
119
// This hook is called when a MIDI package has been received
120
/////////////////////////////////////////////////////////////////////////////
121
void APP_MIDI_NotifyPackage(mios32_midi_port_t port, mios32_midi_package_t midi_package)
122
{
123
}
124
 
125
 
126
/////////////////////////////////////////////////////////////////////////////
127
// This hook is called before the shift register chain is scanned
128
/////////////////////////////////////////////////////////////////////////////
129
void APP_SRIO_ServicePrepare(void)
130
{
131
}
132
 
133
 
134
/////////////////////////////////////////////////////////////////////////////
135
// This hook is called after the shift register chain has been scanned
136
/////////////////////////////////////////////////////////////////////////////
137
void APP_SRIO_ServiceFinish(void)
138
{
139
}
140
 
141
 
142
/////////////////////////////////////////////////////////////////////////////
143
// This hook is called when a button has been toggled
144
// pin_value is 1 when button released, and 0 when button pressed
145
/////////////////////////////////////////////////////////////////////////////
146
void APP_DIN_NotifyToggle(u32 pin, u32 pin_value)
147
{
148
}
149
 
150
 
151
/////////////////////////////////////////////////////////////////////////////
152
// This hook is called when an encoder has been moved
153
// incrementer is positive when encoder has been turned clockwise, else
154
// it is negative
155
/////////////////////////////////////////////////////////////////////////////
156
void APP_ENC_NotifyChange(u32 encoder, s32 incrementer)
157
{
158
}
159
 
160
 
161
/////////////////////////////////////////////////////////////////////////////
162
// This hook is called when a pot has been moved
163
/////////////////////////////////////////////////////////////////////////////
164
void APP_AIN_NotifyChange(u32 pin, u32 pin_value)
165
{
166
}
167
 
168
 
169
/////////////////////////////////////////////////////////////////////////////
170
// This DMA callback is called periodically
171
/////////////////////////////////////////////////////////////////////////////
172
static void SRIO_Handler(void)
173
{
174
  // TK: using direct port accesses instead of the comfortable MIOS32_BOARD_J5_PinSet
175
  // functions to speed up the timing critical handler
176
 
177
  // Ports are located at:
178
  // J5A[3:0] -> GPIOC[3:0]
179
  // J5B[3:0] -> GPIOA[3:0]
180
  // J5C[1:0] -> GPIOC[5:4]
181
  // J5C[3:2] -> GPIOB[1:0]
182
 
183
  // BSRR[15:0] sets output register to 1, BSRR[31:16] to 0
184
  // BRR[15:0] sets output register to 0 as well (no shifting required, but multiple accesses required if pins shout be set/cleared)
185
 
186
  //MIOS32_BOARD_J5_PinSet(muxctr , 0);     //jm organ muxpin off 
187
  //MIOS32_BOARD_J5_PinSet(8 , 0);      //jm Dout disabled
188
  GPIOC->BSRR = (1 << (muxctr+16)) | (1 << 4); // clear muxctr pin, set GPIOC[4] = J5C.A8
189
 
190
  //MIOS32_BOARD_J5_PinSet(muxctr + 4 , 1); //jm keyboard mux pin on
191
  GPIOA->BSRR = 1 << muxctr;
192
 
193
 
194
  //latch DOUT registers by pulsing RCLK: 1->0->1
195
  MIOS32_SPI_RC_PinSet(MIOS32_SRIO_SPI, MIOS32_SRIO_SPI_RC_PIN, 0); // spi, rc_pin, pin_value
196
  //MIOS32_DELAY_Wait_uS(1); //(not needed JM)
197
  MIOS32_SPI_RC_PinSet(MIOS32_SRIO_SPI, MIOS32_SRIO_SPI_RC_PIN, 1); // spi, rc_pin, pin_value
198
 
199
  //MIOS32_BOARD_J5_PinSet(muxctr + 4 , 0); //jm keyboard mux pin off
200
  GPIOA->BRR = 1 << muxctr;
201
 
202
  //JM Mux counter 
203
  // TK: remember the previous one for DIN buffer copies
204
  u8 prev_muxctr = muxctr;
205
  if ( ++muxctr >= 4 ) {
206
    muxctr = 0;
207
  }  
208
 
209
  //mux pin on     
210
  //MIOS32_BOARD_J5_PinSet(muxctr , 1);     //jm organ mux pin on
211
  //MIOS32_BOARD_J5_PinSet(8 , 1);      //jm Dout enabled
212
  GPIOC->BSRR = 1 << muxctr | (1 << 4);
213
 
214
 
215
  // TK: not optimized as this seems to be a test option which will be removed later?
216
  // disable it to measure best-case timing
217
#if 0
218
  if (MIOS32_BOARD_J5_PinGet(11) == 0) {    //test for mode 1
219
      MIOS32_BOARD_J5_PinSet(muxctr + 4 , 1);   //jm set keyboard mux pin on mode 1
220
  }
221
#endif
222
 
223
  // start next SRIO Scan
224
  // we use J5.A3 for debugging
225
  MIOS32_SPI_TransferBlock(MIOS32_SRIO_SPI,
226
               (u8 *)&srio_dout[muxctr][0], (u8 *)&srio_din_buffer[muxctr][0],  //jm todo ??
227
               MIOS32_SRIO_NUM_SR,
228
               SRIO_Handler);
229
 
230
  // copy/or buffered DIN values/changed flags of previous scan
231
  int i;
232
  for(i=0; i<MIOS32_SRIO_NUM_SR; ++i) {
233
    srio_din_changed[prev_muxctr][i] |= srio_din[prev_muxctr][i] ^ srio_din_buffer[prev_muxctr][i];
234
    srio_din[prev_muxctr][i] = srio_din_buffer[prev_muxctr][i];
235
  }
236
}
237
 
238
 
239
/////////////////////////////////////////////////////////////////////////////
240
// This low-prio task is running endless to check for DIN changes
241
/////////////////////////////////////////////////////////////////////////////
242
static void TASK_DIN_Handler(void *pvParameters)
243
{
244
  s32 mux;
245
  s32 sr;
246
  s32 sr_pin;
247
  u8 changed;
248
 
249
  // endless loop
250
  while( 1 ) {
251
    // toggle the state of all LEDs (allows to measure the execution speed with a scope)
252
    MIOS32_BOARD_LED_Set(0xffffffff, ~MIOS32_BOARD_LED_Get());
253
 
254
    // check all shift registers for DIN pin changes
255
    for(mux=0; mux<4; ++mux) {
256
      for(sr=0; sr<MIOS32_SRIO_NUM_SR; ++sr) {
257
 
258
    // check if there are pin changes (mask all pins)
259
    // must be atomic!
260
    MIOS32_IRQ_Disable();
261
    changed = srio_din_changed[mux][sr];
262
    srio_din_changed[mux][sr] = 0;
263
    MIOS32_IRQ_Enable();
264
 
265
    // any pin change at this SR?
266
    if( !changed )
267
      continue;
268
 
269
    // check all 8 pins of the SR
270
    for(sr_pin=0; sr_pin<8; ++sr_pin)
271
      if( changed & (1 << sr_pin) ) {
272
        // call the notification function
273
        u32 pin = MIOS32_SRIO_NUM_SR*8*mux + 8*sr + sr_pin;
274
        u32 pin_value = (srio_din[mux][sr] & (1 << sr_pin)) ? 1 : 0;
275
        APP_DIN_NotifyToggle(pin, pin_value);
276
      }
277
      }
278
    }
279
  }
280
}
281