Browse Source

cmDevCfg.h/c: Many changes and additions. Implemented 'locattions'.

master
kevin 11 years ago
parent
commit
ac23cc8fb9
2 changed files with 556 additions and 126 deletions
  1. 533
    117
      cmDevCfg.c
  2. 23
    9
      cmDevCfg.h

+ 533
- 117
cmDevCfg.c View File

@@ -1,12 +1,19 @@
1 1
 #include "cmGlobal.h"
2
+#include "cmFloatTypes.h"
2 3
 #include "cmRpt.h"
3 4
 #include "cmErr.h"
4 5
 #include "cmCtx.h"
5 6
 #include "cmMem.h"
6 7
 #include "cmMallocDebug.h"
7 8
 #include "cmJson.h"
9
+#include "cmThread.h"
8 10
 #include "cmMidi.h"
9 11
 #include "cmMidiPort.h"
12
+#include "cmAudioPort.h"
13
+#include "cmUdpPort.h"
14
+#include "cmUdpNet.h"
15
+#include "cmAudioSysMsg.h"
16
+#include "cmAudioSys.h"
10 17
 
11 18
 #include "cmDevCfg.h"
12 19
 
@@ -28,12 +35,9 @@ typedef struct
28 35
   cmChar_t* dcLabelStr;        // Name of this cfg record or NULL if the recd is inactive.
29 36
   cmChar_t* inDevLabelStr;     // Input audio device label.
30 37
   cmChar_t* outDevLabelStr;    // Output audio device label.
31
-  bool      syncToInputFl;     // 'True' if the audio system should sync to the input port.
32
-  unsigned  msgQueueByteCnt;   // Audio system msg queue in bytes.
33
-  unsigned  devFramesPerCycle; // Audio system sample frames per device callback.
34
-  unsigned  dspFramesPerCycle; // DSP system samples per block.
35
-  unsigned  audioBufCnt;       // Count of audio buffers (of size devFramesPerCycle) 
36
-  double    srate;             // Audio system sample rate.
38
+
39
+  cmAudioSysArgs_t ss;
40
+  
37 41
 } cmDcmAudio_t;
38 42
 
39 43
 typedef struct              
@@ -47,8 +51,8 @@ typedef struct
47 51
 typedef struct
48 52
 {
49 53
   cmTypeDcmId_t tid;      // Type Id for this map or tInvalidDcmTId if the record is not active.
50
-  unsigned   usrDevId; // Same as index into p->map[] for this recd.
51
-  unsigned   cfgIndex; // Index into p->midi[],p->audio[], or p->net[].
54
+  unsigned      usrDevId; // Same as index into p->map[] for this recd.
55
+  unsigned      cfgIndex; // Index into p->midi[],p->audio[], or p->net[].
52 56
 } cmDcmMap_t;
53 57
 
54 58
 typedef struct
@@ -61,7 +65,7 @@ typedef struct
61 65
 
62 66
 typedef struct
63 67
 {
64
-  cmErr_t       err;
68
+  cmChar_t*     labelStr;
65 69
 
66 70
   cmDcmApp_t*   app;
67 71
   unsigned      appCnt;
@@ -74,6 +78,18 @@ typedef struct
74 78
 
75 79
   cmDcmNet_t*   net;
76 80
   unsigned      netCnt;
81
+
82
+} cmDcmLoc_t;
83
+
84
+typedef struct
85
+{
86
+  cmErr_t      err;
87
+
88
+  cmDcmLoc_t*  loc;
89
+  unsigned     locCnt;
90
+
91
+  cmDcmLoc_t*  l;
92
+
77 93
 } cmDcm_t;
78 94
 
79 95
 cmDcm_t* _cmDcmHandleToPtr( cmDevCfgH_t h )
@@ -83,6 +99,23 @@ cmDcm_t* _cmDcmHandleToPtr( cmDevCfgH_t h )
83 99
   return p;
84 100
 }
85 101
 
102
+void _cmDcmAppDupl( cmDcmApp_t* d, const cmDcmApp_t* s )
103
+{
104
+  *d = *s;
105
+  if( d->activeFl )
106
+  {
107
+    unsigned i;
108
+    d->map = cmMemAllocZ(cmDcmMap_t,s->mapCnt);
109
+    for(i=0; i<s->mapCnt; ++i)
110
+      d->map[i] = s->map[i];
111
+  }
112
+  else
113
+  {
114
+    d->mapCnt = 0;
115
+    d->map    = NULL;
116
+  }
117
+}
118
+
86 119
 void _cmDcmMidiFree( cmDcmMidi_t* r )
87 120
 {
88 121
   cmMemPtrFree(&r->dcLabelStr);
@@ -90,6 +123,16 @@ void _cmDcmMidiFree( cmDcmMidi_t* r )
90 123
   cmMemPtrFree(&r->portLabelStr);
91 124
 }
92 125
 
126
+void _cmDcmMidiDupl( cmDcmMidi_t* d, const cmDcmMidi_t* s )
127
+{
128
+  d->dcLabelStr   = cmMemAllocStr(s->dcLabelStr);
129
+  d->devLabelStr  = cmMemAllocStr(s->devLabelStr);
130
+  d->portLabelStr = cmMemAllocStr(s->portLabelStr);
131
+  d->inputFl      = s->inputFl;
132
+  d->devIdx       = s->devIdx;
133
+  d->portIdx      = s->portIdx;
134
+}
135
+
93 136
 void _cmDcmAudioFree( cmDcmAudio_t* r )
94 137
 {
95 138
   cmMemPtrFree(&r->dcLabelStr);
@@ -97,48 +140,86 @@ void _cmDcmAudioFree( cmDcmAudio_t* r )
97 140
   cmMemPtrFree(&r->outDevLabelStr);
98 141
 }
99 142
 
143
+void _cmDcmAudioDupl( cmDcmAudio_t* d, const cmDcmAudio_t* s )
144
+{
145
+  d->dcLabelStr = cmMemAllocStr(s->dcLabelStr);
146
+  d->inDevLabelStr = cmMemAllocStr(s->inDevLabelStr);
147
+  d->outDevLabelStr = cmMemAllocStr(s->outDevLabelStr);
148
+  d->ss             = s->ss;
149
+}
150
+
100 151
 void _cmDcmNetFree( cmDcmNet_t* r )
101 152
 {
102 153
   cmMemPtrFree(&r->dcLabelStr);
103 154
   cmMemPtrFree(&r->sockAddr);
104 155
 }
105 156
 
157
+void _cmDcmNetDupl( cmDcmNet_t* d, const cmDcmNet_t* s )
158
+{
159
+  d->dcLabelStr = cmMemAllocStr(s->dcLabelStr);
160
+  d->sockAddr   = cmMemAllocStr(s->sockAddr);
161
+  d->portNumber = s->portNumber;
162
+  d->netNodeId  = s->netNodeId;
163
+}
164
+
106 165
 void _cmDcmAppFree( cmDcmApp_t* r )
107 166
 {
108 167
   cmMemPtrFree(&r->map);
109 168
 }
110 169
 
111
-cmDcRC_t _cmDcmFree( cmDcm_t* p )
170
+cmDcRC_t  _cmDcmFreeLoc( cmDcm_t* p, cmDcmLoc_t* loc )
112 171
 {
113 172
   unsigned i;
114 173
 
115
-  for(i=0; p->midi!=NULL && i<p->midiCnt; ++i)
116
-    _cmDcmMidiFree(p->midi + i );
117
-  cmMemPtrFree(&p->midi);
174
+  for(i=0; loc->midi!=NULL && i<loc->midiCnt; ++i)
175
+    _cmDcmMidiFree(loc->midi + i );
176
+  cmMemPtrFree(&loc->midi);
177
+  loc->midiCnt = 0;
118 178
 
119
-  for(i=0; p->audio!=NULL && i<p->audioCnt; ++i)
120
-    _cmDcmAudioFree(p->audio + i );
121
-  cmMemPtrFree(&p->audio);
179
+  for(i=0; loc->audio!=NULL && i<loc->audioCnt; ++i)
180
+    _cmDcmAudioFree(loc->audio + i );
181
+  cmMemPtrFree(&loc->audio);
182
+  loc->audioCnt = 0;
122 183
 
123
-  for(i=0; p->net!=NULL && i<p->netCnt; ++i)
124
-    _cmDcmNetFree(p->net + i );
125
-  cmMemPtrFree(&p->net);
184
+  for(i=0; loc->net!=NULL && i<loc->netCnt; ++i)
185
+    _cmDcmNetFree(loc->net + i );
186
+  cmMemPtrFree(&loc->net);
187
+  loc->netCnt = 0;
126 188
 
127
-  for(i=0; p->app!=NULL && i<p->appCnt; ++i)
128
-    _cmDcmAppFree(p->app + i );
129
-  cmMemPtrFree(&p->app);
130
-  
131
-  return kOkDcRC;
189
+  for(i=0; loc->app!=NULL && i<loc->appCnt; ++i)
190
+    _cmDcmAppFree(loc->app + i );
191
+  cmMemPtrFree(&loc->app);
192
+  loc->appCnt = 0;
193
+
194
+  cmMemPtrFree(&loc->labelStr);
195
+
196
+  return kOkDcRC;  
197
+}
198
+
199
+cmDcRC_t _cmDcmFree( cmDcm_t* p )
200
+{
201
+  cmDcRC_t rc = kOkDcRC;
202
+  unsigned i;
203
+
204
+  for(i=0; i<p->locCnt; ++i)
205
+    if((rc = _cmDcmFreeLoc(p,p->loc + i )) != kOkDcRC )
206
+      return rc;
207
+
208
+  cmMemPtrFree(&p->loc);
209
+
210
+  return rc;
132 211
 }
133 212
 
213
+
214
+
134 215
 cmDcmMidi_t* _cmDcmMidiFind( cmDcm_t* p, const cmChar_t* dcLabelStr, bool errFl )
135 216
 {
136 217
   assert( dcLabelStr != NULL );
137 218
 
138 219
   unsigned i;
139
-  for(i=0; i<p->midiCnt; ++i)
140
-    if(p->midi[i].dcLabelStr!=NULL && strcmp(p->midi[i].dcLabelStr,dcLabelStr)==0)
141
-      return p->midi + i;
220
+  for(i=0; i<p->l->midiCnt; ++i)
221
+    if(p->l->midi[i].dcLabelStr!=NULL && strcmp(p->l->midi[i].dcLabelStr,dcLabelStr)==0)
222
+      return p->l->midi + i;
142 223
 
143 224
   if( errFl )
144 225
     cmErrMsg(&p->err,cmLabelNotFoundDcRC,"The MIDI cfg. record '%s' not found.",dcLabelStr);
@@ -151,9 +232,9 @@ cmDcmAudio_t* _cmDcmAudioFind( cmDcm_t* p, const cmChar_t* dcLabelStr, bool errF
151 232
   assert( dcLabelStr != NULL );
152 233
 
153 234
   unsigned i;
154
-  for(i=0; i<p->audioCnt; ++i)
155
-    if(p->audio[i].dcLabelStr!=NULL && strcmp(p->audio[i].dcLabelStr,dcLabelStr)==0)
156
-      return p->audio + i;
235
+  for(i=0; i<p->l->audioCnt; ++i)
236
+    if(p->l->audio[i].dcLabelStr!=NULL && strcmp(p->l->audio[i].dcLabelStr,dcLabelStr)==0)
237
+      return p->l->audio + i;
157 238
 
158 239
   if( errFl )
159 240
     cmErrMsg(&p->err,cmLabelNotFoundDcRC,"The audio cfg. record '%s' not found.",dcLabelStr);
@@ -166,9 +247,9 @@ cmDcmNet_t* _cmDcmNetFind( cmDcm_t* p, const cmChar_t* dcLabelStr, bool errFl )
166 247
   assert( dcLabelStr != NULL );
167 248
 
168 249
   unsigned i;
169
-  for(i=0; i<p->netCnt; ++i)
170
-    if(p->net[i].dcLabelStr!=NULL && strcmp(p->net[i].dcLabelStr,dcLabelStr)==0)
171
-      return p->net + i;
250
+  for(i=0; i<p->l->netCnt; ++i)
251
+    if(p->l->net[i].dcLabelStr!=NULL && strcmp(p->l->net[i].dcLabelStr,dcLabelStr)==0)
252
+      return p->l->net + i;
172 253
 
173 254
   if( errFl )
174 255
     cmErrMsg(&p->err,cmLabelNotFoundDcRC,"The net cfg. record '%s' not found.",dcLabelStr);
@@ -180,13 +261,13 @@ cmDcmNet_t* _cmDcmNetFind( cmDcm_t* p, const cmChar_t* dcLabelStr, bool errFl )
180 261
 cmDcmApp_t*  _cmDcmFindOrCreateApp(cmDcm_t* p, unsigned usrAppId ) 
181 262
 {
182 263
   cmDcmApp_t* a;
183
-  if( usrAppId < p->appCnt )
184
-    a = p->app + usrAppId;
264
+  if( usrAppId < p->l->appCnt )
265
+    a = p->l->app + usrAppId;
185 266
   else
186 267
   {
187
-    p->appCnt = usrAppId + 1;
188
-    p->app    = cmMemResizePZ(cmDcmApp_t,p->app,p->appCnt);
189
-    a = p->app + usrAppId;
268
+    p->l->appCnt = usrAppId + 1;
269
+    p->l->app    = cmMemResizePZ(cmDcmApp_t,p->l->app,p->l->appCnt);
270
+    a = p->l->app + usrAppId;
190 271
     a->usrAppId = usrAppId;
191 272
     a->activeFl = true;    
192 273
   }
@@ -214,14 +295,14 @@ cmDcmMap_t* _cmDcmFindOrCreateMap(cmDcm_t* p, cmDcmApp_t* a, unsigned usrDevId )
214 295
 cmDcRC_t  _cmDcmLookupApp(cmDcm_t* p, unsigned usrAppId, cmDcmApp_t** appRef)
215 296
 {
216 297
   // validate the usrAppId
217
-  if( usrAppId >= p->appCnt )
298
+  if( usrAppId >= p->l->appCnt )
218 299
     return cmErrMsg(&p->err,kInvalidDevArgDcRC,"Invalid user app. id:%i\n",usrAppId);
219 300
 
220 301
   // check that the app recd is active
221
-  if( p->app[usrAppId].activeFl == false )
302
+  if( p->l->app[usrAppId].activeFl == false )
222 303
     return cmErrMsg(&p->err,kInvalidDevArgDcRC,"The user app. with id:%i is not active.",usrAppId);
223 304
 
224
-  *appRef = p->app + usrAppId;
305
+  *appRef = p->l->app + usrAppId;
225 306
 
226 307
   return kOkDcRC;
227 308
 }
@@ -255,18 +336,98 @@ cmDcRC_t  _cmDcmLookupAppMap(cmDcm_t* p, unsigned usrAppId, unsigned usrDevId, c
255 336
 void _cmDevCfgDeleteCfgMaps( cmDcm_t* p, cmTypeDcmId_t tid, unsigned cfgIndex )
256 337
 {
257 338
   unsigned i,j;
258
-  for(i=0; i<p->appCnt; ++i)
259
-    if( p->app[i].activeFl )
260
-      for(j=0; j<p->app[i].mapCnt; ++j)
261
-        if( p->app[i].map[j].tid == tid && p->app[i].map[j].cfgIndex == cfgIndex )
339
+  for(i=0; i<p->l->appCnt; ++i)
340
+    if( p->l->app[i].activeFl )
341
+      for(j=0; j<p->l->app[i].mapCnt; ++j)
342
+        if( p->l->app[i].map[j].tid == tid && p->l->app[i].map[j].cfgIndex == cfgIndex )
262 343
         {
263
-          p->app[i].map[j].tid = kInvalidDcmTId;
344
+          p->l->app[i].map[j].tid = kInvalidDcmTId;
264 345
           break;
265 346
         }
266 347
 }
267 348
 
349
+cmDcRC_t _cmDcmFindCfgIndex( cmDcm_t* p, cmTypeDcmId_t tid, const cmChar_t* dcLabelStr, unsigned* cfgIndexRef )
350
+{
351
+  cmDcRC_t rc = kOkDcRC;
352
+
353
+  *cfgIndexRef = cmInvalidIdx;
354
+
355
+  switch( tid )
356
+  {
357
+    case kMidiDcmTId:
358
+      {
359
+        const cmDcmMidi_t* r;
360
+
361
+        if((r = _cmDcmMidiFind(p,dcLabelStr,true)) == NULL )
362
+          rc = cmErrLastRC(&p->err);
363
+        else
364
+          *cfgIndexRef = r - p->l->midi;
365
+      }
366
+      break;
367
+
368
+    case kAudioDcmTId:
369
+      {
370
+        const cmDcmAudio_t* r;
371
+
372
+        if((r = _cmDcmAudioFind(p,dcLabelStr,true)) == NULL )
373
+          rc = cmErrLastRC(&p->err);
374
+        else
375
+          *cfgIndexRef = r - p->l->audio;
376
+      }
377
+      break;
378
+
379
+    case kNetDcmTId:
380
+      {
381
+        const cmDcmNet_t* r;
382
+
383
+        if((r = _cmDcmNetFind(p,dcLabelStr,true)) == NULL )
384
+          rc = cmErrLastRC(&p->err);
385
+        else
386
+          *cfgIndexRef = r - p->l->net;
387
+      }
388
+      break;
389
+      
390
+    default:
391
+      assert(0);
392
+      break;
393
+  }
394
+
395
+  return rc;
396
+}
397
+
398
+cmDcRC_t _cmDevCfgDeleteCfg( cmDcm_t* p, cmTypeDcmId_t tid, unsigned cfgIndex )
399
+{
400
+  // release any resources held by this cfg record and mark
401
+  // the record as inactive by setting the dcLabelStr field to NULL.
402
+  switch( tid )
403
+  {
404
+    case kMidiDcmTId:
405
+      _cmDcmMidiFree( p->l->midi + cfgIndex );
406
+      break;
407
+
408
+    case kAudioDcmTId:
409
+      _cmDcmAudioFree( p->l->audio + cfgIndex );
410
+      break;
411
+
412
+    case kNetDcmTId:
413
+      _cmDcmNetFree( p->l->net + cfgIndex );
414
+      break;
415
+      
416
+    default:
417
+      assert(0);
418
+      break;
419
+  }
420
+
421
+  // delete all maps which reference this cfg recd
422
+  if( cfgIndex != cmInvalidIdx )
423
+    _cmDevCfgDeleteCfgMaps(p, tid, cfgIndex );
424
+  
425
+
426
+  return kOkDcRC;
427
+}
428
+
268 429
 
269
-cmDcRC_t cmDevCfgMgrAlloc( cmCtx_t* ctx, cmDevCfgH_t* hp, cmJsonH_t jsH )
430
+cmDcRC_t cmDevCfgMgrAlloc( cmCtx_t* ctx, cmDevCfgH_t* hp )
270 431
 {
271 432
   cmDcRC_t rc;
272 433
   if((rc = cmDevCfgMgrFree(hp)) != kOkDcRC )
@@ -275,6 +436,10 @@ cmDcRC_t cmDevCfgMgrAlloc( cmCtx_t* ctx, cmDevCfgH_t* hp, cmJsonH_t jsH )
275 436
   cmDcm_t* p = cmMemAllocZ(cmDcm_t,1);
276 437
   cmErrSetup(&p->err,&ctx->rpt,"DevCfgMgr");
277 438
 
439
+  p->loc         = cmMemAllocZ(cmDcmLoc_t,1);
440
+  p->locCnt      = 1;
441
+  p->l           = p->loc;
442
+  p->l->labelStr = cmMemAllocStr("Default");
278 443
 
279 444
   hp->h = p;
280 445
 
@@ -289,7 +454,7 @@ cmDcRC_t cmDevCfgMgrFree( cmDevCfgH_t* hp )
289 454
 {
290 455
   cmDcRC_t rc = kOkDcRC;
291 456
 
292
-  if(hp!=NULL || cmDevCfgIsValid(*hp))
457
+  if(hp==NULL || cmDevCfgIsValid(*hp)==false)
293 458
     return rc;
294 459
 
295 460
   cmDcm_t* p = _cmDcmHandleToPtr(*hp);
@@ -307,86 +472,97 @@ cmDcRC_t cmDevCfgMgrFree( cmDevCfgH_t* hp )
307 472
 cmDcRC_t cmDevCfgIsValid( cmDevCfgH_t h )
308 473
 { return h.h != NULL; }
309 474
 
310
-cmDcRC_t _cmDcmFindCfgIndex( cmDcm_t* p, cmTypeDcmId_t tid, const cmChar_t* dcLabelStr, unsigned* cfgIndexRef )
475
+unsigned cmDevCfgCount( cmDevCfgH_t h, cmTypeDcmId_t typeId )
311 476
 {
312
-  cmDcRC_t rc = kOkDcRC;
313
-
314
-  *cfgIndexRef = cmInvalidIdx;
477
+  cmDcm_t* p        = _cmDcmHandleToPtr(h);
478
+  unsigned n = 0;
479
+  unsigned i;
315 480
 
316
-  switch( tid )
481
+  switch( typeId )
317 482
   {
318 483
     case kMidiDcmTId:
319
-      {
320
-        const cmDcmMidi_t* r;
321
-
322
-        if((r = _cmDcmMidiFind(p,dcLabelStr,true)) == NULL )
323
-          rc = cmErrLastRC(&p->err);
324
-        else
325
-          *cfgIndexRef = r - p->midi;
326
-      }
484
+      for(i=0; i<p->l->midiCnt; ++i)
485
+        if( p->l->midi[i].dcLabelStr != NULL )
486
+          ++n;
327 487
       break;
328 488
 
329 489
     case kAudioDcmTId:
330
-      {
331
-        const cmDcmAudio_t* r;
332
-
333
-        if((r = _cmDcmAudioFind(p,dcLabelStr,true)) == NULL )
334
-          rc = cmErrLastRC(&p->err);
335
-        else
336
-          *cfgIndexRef = r - p->audio;
337
-      }
490
+      for(i=0; i<p->l->audioCnt; ++i)
491
+        if( p->l->audio[i].dcLabelStr != NULL )
492
+          ++n;
338 493
       break;
339 494
 
340 495
     case kNetDcmTId:
341
-      {
342
-        const cmDcmNet_t* r;
343
-
344
-        if((r = _cmDcmNetFind(p,dcLabelStr,true)) == NULL )
345
-          rc = cmErrLastRC(&p->err);
346
-        else
347
-          *cfgIndexRef = r - p->net;
348
-      }
496
+      for(i=0; i<p->l->netCnt; ++i)
497
+        if( p->l->net[i].dcLabelStr != NULL )
498
+          ++n;
349 499
       break;
350
-      
500
+
351 501
     default:
352 502
       assert(0);
353 503
       break;
354 504
   }
355 505
 
356
-  return rc;
506
+  return n;
357 507
 }
358 508
 
359
-cmDcRC_t _cmDevCfgDeleteCfg( cmDcm_t* p, cmTypeDcmId_t tid, unsigned cfgIndex )
509
+const cmChar_t* cmDevCfgLabel( cmDevCfgH_t h, cmTypeDcmId_t typeId, unsigned index )
360 510
 {
361
-  // release any resources held by this cfg record and mark
362
-  // the record as inactive by setting the dcLabelStr field to NULL.
363
-  switch( tid )
511
+  cmDcm_t* p        = _cmDcmHandleToPtr(h);
512
+  int j = -1;
513
+  unsigned i;
514
+  unsigned n = 0;
515
+  const cmChar_t* s;
516
+
517
+  switch( typeId )
364 518
   {
365 519
     case kMidiDcmTId:
366
-      _cmDcmMidiFree( p->midi + cfgIndex );
520
+      n = p->l->midiCnt;
521
+      for(i=0; i<n; ++i)
522
+        if( (s = p->l->midi[i].dcLabelStr) != NULL )
523
+          if(++j == index )
524
+            break;
525
+
367 526
       break;
368 527
 
369 528
     case kAudioDcmTId:
370
-      _cmDcmAudioFree( p->audio + cfgIndex );
529
+      n = p->l->audioCnt;
530
+      for(i=0; i<n; ++i)
531
+        if( (s = p->l->audio[i].dcLabelStr) != NULL )
532
+          if(++j == index )
533
+            break;
371 534
       break;
372 535
 
373 536
     case kNetDcmTId:
374
-      _cmDcmNetFree( p->net + cfgIndex );
537
+      n = p->l->netCnt;
538
+      for(i=0; i<n; ++i)
539
+        if( (s = p->l->net[i].dcLabelStr) != NULL )
540
+          if(++j == index )
541
+            break;
375 542
       break;
376
-      
377 543
     default:
378 544
       assert(0);
379 545
       break;
380 546
   }
381 547
 
382
-  // delete all maps which reference this cfg recd
383
-  if( cfgIndex != cmInvalidIdx )
384
-    _cmDevCfgDeleteCfgMaps(p, tid, cfgIndex );
385
-  
548
+  if( i == n )
549
+    return NULL;
386 550
 
387
-  return kOkDcRC;
551
+  return s;
388 552
 }
389 553
 
554
+unsigned cmDevCfgLabelToIndex( cmDevCfgH_t h, cmTypeDcmId_t tid, const cmChar_t* dcLabelStr )
555
+{
556
+  cmDcm_t* p        = _cmDcmHandleToPtr(h);
557
+  unsigned cfgIdx = cmInvalidIdx;
558
+
559
+  if( _cmDcmFindCfgIndex( p, tid, dcLabelStr, &cfgIdx ) != kOkDcRC )
560
+    return cmInvalidIdx;
561
+
562
+  return cfgIdx;
563
+}
564
+
565
+
390 566
 cmDcRC_t cmDevCfgDeleteCfg(  cmDevCfgH_t h, cmTypeDcmId_t tid, const cmChar_t* dcLabelStr )
391 567
 {
392 568
   cmDcRC_t rc;
@@ -459,42 +635,42 @@ cmDcRC_t cmDevCfgNameMidiPort(
459 635
   const cmChar_t* portNameStr,
460 636
   bool            inputFl )
461 637
 {
462
-  cmDcRC_t    rc = kOkDcRC;
638
+  cmDcRC_t    rc  = kOkDcRC;
463 639
   cmDcm_t*     p  = _cmDcmHandleToPtr(h);
464 640
   cmDcmMidi_t* r  = _cmDcmMidiFind(p,dcLabelStr,false);
465 641
   unsigned     i;
466 642
 
467 643
   // if 'dcLabelStr' was not already used then look for an empty MIDI record.
468 644
   if( r == NULL )
469
-    for(i=0; i<p->midiCnt; ++i)
470
-      if( p->midi[i].dcLabelStr == NULL )
645
+    for(i=0; i<p->l->midiCnt; ++i)
646
+      if( p->l->midi[i].dcLabelStr == NULL )
471 647
       {
472
-        r = p->midi + i;
648
+        r = p->l->midi + i;
473 649
         break;
474 650
       }
475 651
   
476 652
   // if no available cfg record exists then create one 
477 653
   if( r == NULL )
478 654
   {
479
-    p->midi     = cmMemResizePZ(cmDcmMidi_t,p->midi,p->midiCnt+1);    
480
-    r           = p->midi + p->midiCnt;
481
-    p->midiCnt += 1;
655
+    p->l->midi     = cmMemResizePZ(cmDcmMidi_t,p->l->midi,p->l->midiCnt+1);    
656
+    r           = p->l->midi + p->l->midiCnt;
657
+    p->l->midiCnt += 1;
482 658
   }
483 659
 
484 660
  
485 661
   assert( r != NULL );
486 662
  
487 663
   // verify that the device label is valid
488
-  if((r->devIdx = cmMpDeviceNameToIndex( r->devLabelStr )) == cmInvalidIdx )
664
+  if((r->devIdx = cmMpDeviceNameToIndex( devNameStr )) == cmInvalidIdx )
489 665
   {
490
-    rc = cmErrMsg(&p->err, kInvalidDevArgDcRC,"The MIDI device name '%s' is not valid.",r->devLabelStr);
666
+    rc = cmErrMsg(&p->err, kInvalidDevArgDcRC,"The MIDI device name '%s' is not valid.",devNameStr);
491 667
     goto errLabel;
492 668
   }
493 669
 
494 670
   // verify that the port label is valid
495
-  if((r->portIdx = cmMpDevicePortNameToIndex( r->devIdx, r->inputFl ? kInMpFl : kOutMpFl, r->portLabelStr )) == cmInvalidIdx )
671
+  if((r->portIdx = cmMpDevicePortNameToIndex( r->devIdx, r->inputFl ? kInMpFl : kOutMpFl, portNameStr )) == cmInvalidIdx )
496 672
   {
497
-    rc = cmErrMsg(&p->err, kInvalidDevArgDcRC,"The MIDI port name '%s' is not valid on the device '%s'.",r->portLabelStr,r->devLabelStr);
673
+    rc = cmErrMsg(&p->err, kInvalidDevArgDcRC,"The MIDI port name '%s' is not valid on the device '%s'.",portNameStr,devNameStr);
498 674
     goto errLabel;
499 675
   }
500 676
 
@@ -510,7 +686,7 @@ cmDcRC_t cmDevCfgNameMidiPort(
510 686
  errLabel:
511 687
   // on error delete the cfg record and any maps depending on it
512 688
   if( rc != kOkDcRC && r != NULL )
513
-    _cmDevCfgDeleteCfg( p, kMidiDcmTId, r - p->midi );
689
+    _cmDevCfgDeleteCfg( p, kMidiDcmTId, r - p->l->midi );
514 690
 
515 691
   return rc;
516 692
 }
@@ -525,7 +701,7 @@ cmDcRC_t cmDevCfgMidiDevIdx(    cmDevCfgH_t h, unsigned usrAppId, unsigned usrDe
525 701
   if((rc =  _cmDcmLookupAppMap(p,usrAppId,usrDevId,&m)) != kOkDcRC )
526 702
     return rc;
527 703
                                                 
528
-  cmDcmMidi_t* r = p->midi + m->cfgIndex;
704
+  cmDcmMidi_t* r = p->l->midi + m->cfgIndex;
529 705
 
530 706
   assert(r->dcLabelStr != NULL );
531 707
 
@@ -547,13 +723,83 @@ cmDcRC_t cmDevCfgNameAudioPort(
547 723
   unsigned        audioBufCnt,
548 724
   double          srate  )
549 725
 {
550
-  return kOkDcRC;
726
+  cmDcRC_t     rc  = kOkDcRC;
727
+  cmDcm_t*      p  = _cmDcmHandleToPtr(h);
728
+  cmDcmAudio_t* r  = _cmDcmAudioFind(p,dcLabelStr,false);
729
+  unsigned     i;
730
+
731
+  // if 'dcLabelStr' was not already used then look for an empty audio record.
732
+  if( r == NULL )
733
+    for(i=0; i<p->l->audioCnt; ++i)
734
+      if( p->l->audio[i].dcLabelStr == NULL )
735
+      {
736
+        r = p->l->audio + i;
737
+        break;
738
+      }
739
+  
740
+  // if no available cfg record exists then create one 
741
+  if( r == NULL )
742
+  {
743
+    p->l->audio     = cmMemResizePZ(cmDcmAudio_t,p->l->audio,p->l->audioCnt+1);    
744
+    r           = p->l->audio + p->l->audioCnt;
745
+    p->l->audioCnt += 1;
746
+  }
747
+
748
+ 
749
+  assert( r != NULL );
750
+ 
751
+  // verify that the device label is valid
752
+  if((r->ss.inDevIdx = cmApDeviceLabelToIndex( inDevNameStr )) == cmInvalidIdx )
753
+  {
754
+    rc = cmErrMsg(&p->err, kInvalidDevArgDcRC,"The input audio device name '%s' is not valid.",inDevNameStr);
755
+    goto errLabel;
756
+  }
757
+
758
+  // verify that the device label is valid
759
+  if((r->ss.outDevIdx = cmApDeviceLabelToIndex( outDevNameStr )) == cmInvalidIdx )
760
+  {
761
+    rc = cmErrMsg(&p->err, kInvalidDevArgDcRC,"The output audio device name '%s' is not valid.",outDevNameStr);
762
+    goto errLabel;
763
+  }
764
+
765
+  // if this cfg recd was not previously active then assign a cfg label
766
+  if( r->dcLabelStr == NULL )
767
+    r->dcLabelStr  = cmMemAllocStr(dcLabelStr);
768
+
769
+  // fill in the cfg recd
770
+  r->inDevLabelStr        = cmMemResizeStr(r->inDevLabelStr,inDevNameStr);
771
+  r->outDevLabelStr       = cmMemResizeStr(r->outDevLabelStr,outDevNameStr);
772
+  r->ss.rpt               = p->err.rpt;
773
+  r->ss.syncInputFl       = syncInputFl;
774
+  r->ss.msgQueueByteCnt   = msgQueueByteCnt;
775
+  r->ss.devFramesPerCycle = devFramesPerCycle;
776
+  r->ss.dspFramesPerCycle = dspFramesPerCycle;
777
+  r->ss.audioBufCnt       = audioBufCnt;
778
+  r->ss.srate             = srate;
779
+
780
+ errLabel:
781
+  // on error delete the cfg record and any maps depending on it
782
+  if( rc != kOkDcRC && r != NULL )
783
+    _cmDevCfgDeleteCfg( p, kAudioDcmTId, r - p->l->audio );
784
+
785
+  return rc;
551 786
 }
552 787
 
553 788
 
554 789
 const struct cmAudioSysArgs_str* cmDevCfgAudioSysArgs( cmDevCfgH_t h, unsigned usrAppId, unsigned usrDevId )
555 790
 {
556
-  return NULL;
791
+  cmDcRC_t   rc = kOkDcRC;
792
+  cmDcm_t*    p = _cmDcmHandleToPtr(h);
793
+  cmDcmMap_t* m;
794
+
795
+  if((rc =  _cmDcmLookupAppMap(p,usrAppId,usrDevId,&m)) != kOkDcRC )
796
+    return NULL;
797
+                                                
798
+  cmDcmAudio_t* r = p->l->audio + m->cfgIndex;
799
+
800
+  assert(r->dcLabelStr != NULL );
801
+  
802
+  return &r->ss;
557 803
 }
558 804
 
559 805
 
@@ -573,32 +819,202 @@ unsigned        cmDevCfgNetNodeId(     cmDevCfgH_t h, unsigned usrAppId, unsigne
573 819
 }
574 820
 
575 821
 
576
-// Preset Management Functions:
577
-unsigned        cmDevCfgPresetCount( cmDevCfgH_t h )
822
+// Loc Management Functions:
823
+unsigned        cmDevCfgLocCount( cmDevCfgH_t h )
578 824
 {
579
-  return 0;
825
+  cmDcm_t*    p = _cmDcmHandleToPtr(h);
826
+  unsigned i;
827
+  unsigned n = 0;
828
+  for(i=0; i<p->locCnt; ++i)
829
+    if( p->loc[i].labelStr != NULL )
830
+      ++n;
831
+
832
+  return n;
833
+}
834
+
835
+const cmChar_t* cmDevCfgLocLabel( cmDevCfgH_t h, unsigned locIdx )
836
+{
837
+  cmDcm_t*    p = _cmDcmHandleToPtr(h);
838
+
839
+  unsigned i;
840
+  int j = -1;
841
+  for(i=0; j<locIdx && i<p->locCnt; ++i)
842
+    if( p->loc[i].labelStr != NULL )
843
+      ++j;
844
+
845
+  if( i == p->locCnt )
846
+    return NULL;
847
+
848
+  return p->loc[i].labelStr;
580 849
 }
581 850
 
582
-const cmChar_t* cmDevCfgPresetLabel( cmDevCfgH_t h, unsigned presetIdx )
851
+cmDcmLoc_t* _cmDcmFindLoc( cmDcm_t* p, const cmChar_t* label )
583 852
 {
853
+  unsigned i=0;
854
+  for(; i<p->locCnt; ++i)
855
+    if( strcmp(p->loc[i].labelStr,label)==0 )
856
+      return p->loc + i;
584 857
   return NULL;
585 858
 }
586 859
 
587
-cmDcRC_t        cmDevCfgStore(       cmDevCfgH_t h, const cmChar_t* presetLabelStr )
860
+cmDcmLoc_t* _cmDcmNewLoc( cmDcm_t* p )
588 861
 {
589
-  return kOkDcRC;
862
+  unsigned i;
863
+  // find a deleted location record
864
+  for(i=0; i<p->locCnt; ++i)
865
+    if( p->loc[i].labelStr == NULL )
866
+      return p->loc + i;
867
+
868
+  // no deleted location records exist so append one to p->loc[].
869
+
870
+  unsigned cli = p->l - p->loc; // store the cur loc recd idx
871
+  p->locCnt += 1;
872
+  p->loc     = cmMemResizeZ(cmDcmLoc_t,p->loc,p->locCnt);
873
+  p->l       = p->loc + cli; // restore the cur loc recd ptr
874
+
875
+  return p->loc + p->locCnt - 1;
590 876
 }
591 877
 
592
-cmDcRC_t        cmDevCfgRecall(      cmDevCfgH_t h, const cmChar_t* presetLabelStr )
878
+// Duplicate *sl and return a ptr to the new loc recd.
879
+cmDcmLoc_t*  _cmDcmDuplLoc( cmDcm_t* p, const cmDcmLoc_t* sl, const cmChar_t* label )
593 880
 {
594
-  return kOkDcRC;
881
+  unsigned i;
882
+
883
+  cmDcmLoc_t* l = _cmDcmNewLoc(p);
884
+
885
+  l->labelStr = cmMemAllocStr(label);
886
+
887
+  l->appCnt   = sl->appCnt;
888
+  l->app      = cmMemAllocZ(cmDcmApp_t,l->appCnt);
889
+  for(i=0; i<l->appCnt; ++i)
890
+    _cmDcmAppDupl(l->app +  i, sl->app + i );
891
+
892
+  l->midiCnt  = sl->midiCnt;
893
+  l->midi     = cmMemAllocZ(cmDcmMidi_t,l->midiCnt);
894
+  for(i=0; i<l->midiCnt; ++i)
895
+    _cmDcmMidiDupl(l->midi + i, sl->midi + i );
896
+
897
+  l->audioCnt = sl->audioCnt;
898
+  l->audio    = cmMemAllocZ(cmDcmAudio_t,l->audioCnt);
899
+  for(i=0; i<l->audioCnt; ++i)
900
+    _cmDcmAudioDupl(l->audio + i, sl->audio + i );
901
+
902
+  l->netCnt   = sl->netCnt;
903
+  l->net      = cmMemAllocZ(cmDcmNet_t,l->netCnt);
904
+  for(i=0; i<l->netCnt; ++i)
905
+    _cmDcmNetDupl(l->net + i, sl->net + i );  
906
+
907
+  return l;
595 908
 }
596 909
 
597
-cmDcRC_t        cmDevCfgDelete(      cmDevCfgH_t h, const cmChar_t* presetLabelStr )
910
+cmDcRC_t        cmDevCfgLocStore( cmDevCfgH_t h, const cmChar_t* locLabelStr )
598 911
 {
599
-  return kOkDcRC;
912
+  cmDcRC_t    rc= kOkDcRC;
913
+  cmDcm_t*    p = _cmDcmHandleToPtr(h);
914
+
915
+  if( locLabelStr==NULL || strlen(locLabelStr)==0)
916
+    return cmErrMsg(&p->err,kEmptyLabelDcRC,"The location label was empty or NULL.");
917
+
918
+  assert(p->l != NULL );
919
+
920
+  // if the location name is the same as the current location name ...
921
+  if( strcmp(locLabelStr,p->l->labelStr)==0 )
922
+    return rc;  // ... there is noting to do
923
+
924
+  // get a ptr (if it exists) to the location already named 'locLabelStr'.
925
+  cmDcmLoc_t* sl = _cmDcmFindLoc(p,locLabelStr);
926
+
927
+  // duplicate the current location
928
+  cmDcmLoc_t* dl = _cmDcmDuplLoc(p, p->l, locLabelStr );
929
+
930
+  // make the new location the current location
931
+  p->l = dl;
932
+
933
+  // if loc with the same name already existed then delete it
934
+  if(sl != NULL )
935
+    _cmDcmFreeLoc(p,sl);
936
+
937
+  return rc;
938
+}
939
+
940
+cmDcRC_t        cmDevCfgLocRecall( cmDevCfgH_t h, const cmChar_t* locLabelStr )
941
+{
942
+  cmDcRC_t    rc = kOkDcRC;
943
+  cmDcm_t*    p  = _cmDcmHandleToPtr(h);
944
+  cmDcmLoc_t* loc;
945
+
946
+  if((loc = _cmDcmFindLoc(p,locLabelStr)) == NULL )
947
+    return cmErrMsg(&p->err,kLocNotFoundDcRC,"The location '%s' could not be found.",cmStringNullGuard(locLabelStr));
948
+
949
+  p->l = loc;
950
+
951
+  return rc;
952
+}
953
+
954
+cmDcRC_t        cmDevCfgLocDelete( cmDevCfgH_t h, const cmChar_t* locLabelStr )
955
+{
956
+  cmDcRC_t    rc = kOkDcRC;
957
+  cmDcm_t*    p  = _cmDcmHandleToPtr(h);
958
+  cmDcmLoc_t* loc;
959
+
960
+  // find the loc to delete
961
+  if((loc = _cmDcmFindLoc(p,locLabelStr)) == NULL )
962
+    return cmErrMsg(&p->err,kLocNotFoundDcRC,"The location '%s' could not be found.",cmStringNullGuard(locLabelStr));
963
+
964
+  // delete the requested loc. recd
965
+  _cmDcmFreeLoc(p,loc);
966
+  
967
+  // if the current location was deleted
968
+  if( loc == p->l )
969
+  {
970
+    unsigned i;
971
+    unsigned cli = (p->l - p->loc) + 1;
972
+    for(i=cli; i<p->locCnt; ++i)
973
+      if( p->loc[i].labelStr != NULL )
974
+      {
975
+        p->l = p->loc + i;
976
+        break;
977
+      }
978
+    
979
+    if( i==p->locCnt )
980
+      for(i=0; i<cli; ++i)
981
+        if( p->loc[i].labelStr != NULL )
982
+        {
983
+          p->l = p->loc + i;
984
+          break;
985
+        }
986
+
987
+    // if everything was deleted
988
+    if( i==cli )
989
+    {
990
+      p->l = p->loc;
991
+      p->l->labelStr = cmMemAllocStr("Default");
992
+    }
993
+    
994
+  }
995
+    
996
+
997
+  return rc;
600 998
 }
601 999
 
1000
+unsigned        cmDevCfgLocIndex(  cmDevCfgH_t h )
1001
+{
1002
+  cmDcm_t* p = _cmDcmHandleToPtr(h);
1003
+  unsigned i;
1004
+  int j = -1;
1005
+  for(i=0; i<p->locCnt; ++i)
1006
+  {
1007
+    if( p->loc[i].labelStr != NULL )
1008
+      ++j;
1009
+
1010
+    if( p->loc + i == p->l )
1011
+      return j;
1012
+    
1013
+  }
1014
+
1015
+  assert(0);
1016
+  return cmInvalidIdx;
1017
+}
602 1018
 
603 1019
 cmDcRC_t cmDevCfgWrite( cmDevCfgH_t h )
604 1020
 {

+ 23
- 9
cmDevCfg.h View File

@@ -37,14 +37,16 @@ extern "C" {
37 37
    */
38 38
 
39 39
 
40
-  struct cmAudioSysArgs_t;
40
+  struct cmAudioSysArgs_str;
41 41
 
42 42
   enum
43 43
   {
44 44
     kOkDcRC = cmOkRC,
45 45
     cmLabelNotFoundDcRC,
46 46
     cmIdNotFoundDcRC,
47
-    kInvalidDevArgDcRC
47
+    kInvalidDevArgDcRC,
48
+    kEmptyLabelDcRC,
49
+    kLocNotFoundDcRC
48 50
   };
49 51
 
50 52
   typedef enum
@@ -60,10 +62,18 @@ extern "C" {
60 62
 
61 63
   extern cmDevCfgH_t cmDevCfgNullHandle;
62 64
 
63
-  cmDcRC_t cmDevCfgMgrAlloc( cmCtx_t* c, cmDevCfgH_t* hp, cmJsonH_t jsH );
65
+  cmDcRC_t cmDevCfgMgrAlloc( cmCtx_t* c, cmDevCfgH_t* hp );
64 66
   cmDcRC_t cmDevCfgMgrFree( cmDevCfgH_t* hp );
65 67
   cmDcRC_t cmDevCfgIsValid( cmDevCfgH_t h );
66 68
 
69
+  // Return the count of cfg records for the given type.
70
+  unsigned cmDevCfgCount( cmDevCfgH_t h, cmTypeDcmId_t typeId );
71
+
72
+  // Return the label for a each cfg record of a given type.
73
+  const cmChar_t* cmDevCfgLabel( cmDevCfgH_t h, cmTypeDcmId_t typeId, unsigned index );
74
+
75
+  // Return the cfg index assoc'd with a given label.
76
+  unsigned cmDevCfgLabelToIndex( cmDevCfgH_t h, cmTypeDcmId_t typeId, const cmChar_t* label );
67 77
   
68 78
   // Delete a cfg record created by cmDevCfgNameMidiPort(), cmDevCfgNameAudioPort(), etc.
69 79
   cmDcRC_t cmDevCfgDeleteCfg( cmDevCfgH_t h, cmTypeDcmId_t typeId, const cmChar_t* dcLabelStr );
@@ -75,6 +85,7 @@ extern "C" {
75 85
   // Delete a map record created by cmDevCfgCreateMap().
76 86
   cmDcRC_t cmDevCfgDeleteMap( cmDevCfgH_t h, cmTypeDcmId_t typeId, unsigned usrAppId, unsigned usrDevId );
77 87
   
88
+
78 89
   // Create a MIDI cfg. record.
79 90
   cmDcRC_t cmDevCfgNameMidiPort( 
80 91
     cmDevCfgH_t     h,
@@ -108,14 +119,17 @@ extern "C" {
108 119
 
109 120
   unsigned        cmDevCfgNetNodeId(     cmDevCfgH_t h, unsigned usrAppId, unsigned usrDevId );
110 121
 
111
-  // Preset Management Functions:
122
+  // Location Management Functions:
112 123
   // Store and recall groups cfg records.
113 124
 
114
-  unsigned        cmDevCfgPresetCount( cmDevCfgH_t h );
115
-  const cmChar_t* cmDevCfgPresetLabel( cmDevCfgH_t h, unsigned presetIdx );
116
-  cmDcRC_t        cmDevCfgStore(       cmDevCfgH_t h, const cmChar_t* presetLabelStr );
117
-  cmDcRC_t        cmDevCfgRecall(      cmDevCfgH_t h, const cmChar_t* presetLabelStr );
118
-  cmDcRC_t        cmDevCfgDelete(      cmDevCfgH_t h, const cmChar_t* presetLabelStr );
125
+  unsigned        cmDevCfgLocCount(  cmDevCfgH_t h );
126
+  const cmChar_t* cmDevCfgLocLabel(  cmDevCfgH_t h, unsigned locIdx );
127
+  cmDcRC_t        cmDevCfgLocStore(  cmDevCfgH_t h, const cmChar_t* locLabelStr );
128
+  cmDcRC_t        cmDevCfgLocRecall( cmDevCfgH_t h, const cmChar_t* locLabelStr );
129
+  cmDcRC_t        cmDevCfgLocDelete( cmDevCfgH_t h, const cmChar_t* locLabelStr );
130
+
131
+  // Return the current location index
132
+  unsigned        cmDevCfgLocIndex(  cmDevCfgH_t h );
119 133
 
120 134
   cmDcRC_t cmDevCfgWrite( cmDevCfgH_t h );
121 135
   

Loading…
Cancel
Save