root/branches/streaming-rework/src/libstreaming/AmdtpStreamProcessor.cpp

Revision 392, 60.8 kB (checked in by pieterpalmers, 16 years ago)

- document TimestampedBuffer? class
- partially ported timestamp handling to TimestampedBuffer?
- introduced test for TimestampedBuffer? class

Line 
1 /* $Id$ */
2
3 /*
4  *   FreeBob Streaming API
5  *   FreeBob = Firewire (pro-)audio for linux
6  *
7  *   http://freebob.sf.net
8  *
9  *   Copyright (C) 2005,2006 Pieter Palmers <pieterpalmers@users.sourceforge.net>
10  *
11  *   This program is free software {} you can redistribute it and/or modify
12  *   it under the terms of the GNU General Public License as published by
13  *   the Free Software Foundation {} either version 2 of the License, or
14  *   (at your option) any later version.
15  *
16  *   This program is distributed in the hope that it will be useful,
17  *   but WITHOUT ANY WARRANTY {} without even the implied warranty of
18  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19  *   GNU General Public License for more details.
20  *
21  *   You should have received a copy of the GNU General Public License
22  *   along with this program {} if not, write to the Free Software
23  *   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
24  *
25  *
26  *
27  */
28
29 #include "AmdtpStreamProcessor.h"
30 #include "Port.h"
31 #include "AmdtpPort.h"
32
33 #include "cycletimer.h"
34
35 #include <netinet/in.h>
36 #include <assert.h>
37
38 #define RECEIVE_DLL_INTEGRATION_COEFFICIENT 0.015
39
40 #define RECEIVE_PROCESSING_DELAY (10000U)
41
42 // in ticks
43 #define TRANSMIT_TRANSFER_DELAY 9000U
44 // the number of cycles to send a packet in advance of it's timestamp
45 #define TRANSMIT_ADVANCE_CYCLES 1U
46
47 namespace FreebobStreaming {
48
49 IMPL_DEBUG_MODULE( AmdtpTransmitStreamProcessor, AmdtpTransmitStreamProcessor, DEBUG_LEVEL_NORMAL );
50 IMPL_DEBUG_MODULE( AmdtpReceiveStreamProcessor, AmdtpReceiveStreamProcessor, DEBUG_LEVEL_NORMAL );
51
52
53 /* transmit */
54 AmdtpTransmitStreamProcessor::AmdtpTransmitStreamProcessor(int port, int framerate, int dimension)
55         : TransmitStreamProcessor(port, framerate), m_dimension(dimension)
56         , m_last_timestamp(0), m_dbc(0), m_ringbuffer_size_frames(0)
57 {
58
59 }
60
61 AmdtpTransmitStreamProcessor::~AmdtpTransmitStreamProcessor() {
62
63 }
64
65 /**
66  * @return
67  */
68 bool AmdtpTransmitStreamProcessor::init() {
69
70         debugOutput( DEBUG_LEVEL_VERBOSE, "Initializing (%p)...\n");
71         // call the parent init
72         // this has to be done before allocating the buffers,
73         // because this sets the buffersizes from the processormanager
74         if(!TransmitStreamProcessor::init()) {
75                 debugFatal("Could not do base class init (%p)\n",this);
76                 return false;
77         }
78        
79         return true;
80 }
81
82 void AmdtpTransmitStreamProcessor::setVerboseLevel(int l) {
83         setDebugLevel(l);
84         TransmitStreamProcessor::setVerboseLevel(l);
85 }
86
87 enum raw1394_iso_disposition
88 AmdtpTransmitStreamProcessor::getPacket(unsigned char *data, unsigned int *length,
89                       unsigned char *tag, unsigned char *sy,
90                       int cycle, unsigned int dropped, unsigned int max_length) {
91    
92     struct iec61883_packet *packet = (struct iec61883_packet *) data;
93     unsigned int nevents=0;
94    
95     m_last_cycle=cycle;
96    
97     debugOutput(DEBUG_LEVEL_VERY_VERBOSE,"Xmit handler for cycle %d, (running=%d, enabled=%d,%d)\n",
98         cycle, m_running, m_disabled, m_is_disabled);
99    
100 #ifdef DEBUG
101     if(dropped>0) {
102         debugWarning("Dropped %d packets on cycle %d\n",dropped, cycle);
103     }
104 #endif
105    
106     /* Our node ID can change after a bus reset, so it is best to fetch
107      * our node ID for each packet. */
108     packet->sid = getNodeId() & 0x3f;
109
110     packet->dbs = m_dimension;
111     packet->fn = 0;
112     packet->qpc = 0;
113     packet->sph = 0;
114     packet->reserved = 0;
115     packet->dbc = m_dbc;
116     packet->eoh1 = 2;
117     packet->fmt = IEC61883_FMT_AMDTP;
118
119     // recalculate the buffer head timestamp
120     float ticks_per_frame=m_SyncSource->getTicksPerFrame();
121    
122     // the base timestamp is the one of the last sample in the buffer
123     uint64_t ts_tail;
124     uint64_t fc;
125    
126     m_data_buffer->getBufferTailTimestamp(&ts_tail, &fc); // thread safe
127    
128     int64_t timestamp = ts_tail;
129    
130     // meaning that the first sample in the buffer lies m_framecounter * rate
131     // earlier. This gives the next equation:
132     //   timestamp = m_last_timestamp - m_framecounter * rate
133     timestamp -= (int64_t)((float)fc * ticks_per_frame);
134    
135     // FIXME: test
136 //     timestamp -= (uint64_t)(((float)m_handler->getWakeupInterval())
137 //                                        * ((float)m_syt_interval) * ticks_per_frame);
138 //
139 //     // substract the receive transfer delay
140 //     timestamp -= RECEIVE_PROCESSING_DELAY;
141    
142     // this happens if m_buffer_tail_timestamp wraps around while there are
143     // not much frames in the buffer. We should add the wraparound value of the ticks
144     // counter
145     if (timestamp < 0) {
146         timestamp += TICKS_PER_SECOND * 128L;
147     }
148     // this happens when the last timestamp is near wrapping, and
149     // m_framecounter is low.
150     // this means: m_last_timestamp is near wrapping and have just had
151     // a getPackets() from the client side. the projected next_period
152     // boundary lies beyond the wrap value.
153     // the action is to wrap the value.
154     else if (timestamp >= TICKS_PER_SECOND * 128L) {
155         timestamp -= TICKS_PER_SECOND * 128L;
156     }
157    
158     // determine if we want to send a packet or not
159     // note that we can't use getCycleTimer directly here,
160     // because packets are queued in advance. This means that
161     // we the packet we are constructing will be sent out
162     // on 'cycle', not 'now'.
163     unsigned int ctr=m_handler->getCycleTimer();
164     int now_cycles = (int)CYCLE_TIMER_GET_CYCLES(ctr);
165    
166     // the difference between 'now' and the cycle this
167     // packet is intended for
168     int cycle_diff = cycle - now_cycles;
169    
170     // detect wraparounds
171     if(cycle_diff < -(int)(CYCLES_PER_SECOND/2)) {
172         cycle_diff += CYCLES_PER_SECOND;
173     } else if(cycle_diff > (int)(CYCLES_PER_SECOND/2)) {
174         cycle_diff -= CYCLES_PER_SECOND;
175     }
176
177     // as long as the cycle parameter is not in sync with
178     // the current time, the stream is considered not
179     // to be 'running'
180     if (!m_running && cycle_diff >= 0 && cycle != -1) {
181             debugOutput(DEBUG_LEVEL_VERBOSE, "Xmit StreamProcessor %p started running at cycle %d\n",this, cycle);
182             m_running=true;
183     }
184    
185 #ifdef DEBUG
186     if(cycle_diff < 0) {
187         debugWarning("Requesting packet for cycle %04d which is in the past (now=%04dcy)\n",
188             cycle, now_cycles);
189     }
190 #endif
191     // if cycle lies cycle_diff cycles in the future, we should
192     // queue this packet cycle_diff * TICKS_PER_CYCLE earlier than
193     // we would if it were to be sent immediately.
194    
195     // determine the 'now' time in ticks
196     uint64_t cycle_timer=CYCLE_TIMER_TO_TICKS(ctr);
197    
198     // time until the packet is to be sent (if > 0: send packet)
199     int64_t until_next=timestamp-(int64_t)cycle_timer;
200    
201 #ifdef DEBUG
202     int64_t utn2=until_next; // debug!!
203 #endif
204
205     // we send a packet some cycles in advance, to avoid the
206     // following situation:
207     // suppose we are only a few ticks away from
208     // the moment to send this packet. therefore we decide
209     // not to send the packet, but send it in the next cycle.
210     // This means that the next time point will be 3072 ticks
211     // later, making that the timestamp will be expired when the
212     // packet is sent, unless TRANSFER_DELAY > 3072.
213     // this means that we need at least one cycle of extra buffering.
214     until_next -= TICKS_PER_CYCLE * TRANSMIT_ADVANCE_CYCLES;
215    
216     // we have to queue it cycle_diff * TICKS_PER_CYCLE earlier
217     until_next -= cycle_diff * TICKS_PER_CYCLE;
218
219     // the maximal difference we can allow (64secs)
220     const int64_t max=TICKS_PER_SECOND*64L;
221
222 #ifdef DEBUG
223     if(!m_is_disabled) {
224         debugOutput(DEBUG_LEVEL_VERY_VERBOSE, "=> TS=%11llu, CTR=%11llu, FC=%5d\n",
225             timestamp, cycle_timer, fc
226             );
227         debugOutput(DEBUG_LEVEL_VERY_VERBOSE, "    UTN=%11lld, UTN2=%11lld\n",
228             until_next, utn2
229             );
230         debugOutput(DEBUG_LEVEL_VERY_VERBOSE, "    CY_NOW=%04d, CY_TARGET=%04d, CY_DIFF=%04d\n",
231             now_cycles, cycle, cycle_diff
232             );
233     }
234 #endif
235
236     if(until_next > max) {
237         // this means that cycle_timer has wrapped, but
238         // timestamp has not. we should unwrap cycle_timer
239         // by adding TICKS_PER_SECOND*128L, meaning that we should substract
240         // this value from until_next           
241         until_next -= TICKS_PER_SECOND*128L;
242     } else if (until_next < -max) {
243         // this means that timestamp has wrapped, but
244         // cycle_timer has not. we should unwrap timestamp
245         // by adding TICKS_PER_SECOND*128L, meaning that we should add
246         // this value from until_next
247         until_next += TICKS_PER_SECOND*128L;
248     }
249
250 #ifdef DEBUG
251     if(!m_is_disabled) {
252         debugOutput(DEBUG_LEVEL_VERY_VERBOSE, " > TS=%11llu, CTR=%11llu, FC=%5d\n",
253             timestamp, cycle_timer, fc
254             );
255         debugOutput(DEBUG_LEVEL_VERY_VERBOSE, "    UTN=%11lld, UTN2=%11lld\n",
256             until_next, utn2
257             );
258     }
259 #endif
260
261     if (!m_disabled && m_is_disabled) {
262         // this means that we are trying to enable
263         if ((unsigned int)cycle == m_cycle_to_enable_at) {
264             m_is_disabled=false;
265             debugOutput(DEBUG_LEVEL_VERBOSE,"Enabling StreamProcessor %p at %u\n", this, cycle);
266            
267             // initialize the buffer head & tail
268             uint64_t ts;
269             uint64_t fc;
270            
271             debugOutput(DEBUG_LEVEL_VERBOSE,"Preparing to enable...\n");
272            
273             m_SyncSource->m_data_buffer->getBufferHeadTimestamp(&ts, &fc); // thread safe
274            
275             // the number of cycles the sync source lags
276             // or leads (< 0)
277             int sync_lag_cycles=cycle-m_SyncSource->getLastCycle()-1;
278             if(sync_lag_cycles > (int)(CYCLES_PER_SECOND/2)) {
279                 sync_lag_cycles -= CYCLES_PER_SECOND/2;
280             }
281             if (sync_lag_cycles < -((int)CYCLES_PER_SECOND/2)) {
282                 sync_lag_cycles += CYCLES_PER_SECOND/2;
283             }
284
285             // recalculate the buffer head timestamp
286             float ticks_per_frame=m_SyncSource->getTicksPerFrame();
287
288             // set buffer head timestamp
289             // this makes that the next sample to be sent out
290             // has the same timestamp as the last one received
291             // plus one frame
292             ts += (uint64_t)ticks_per_frame;
293            
294             // account for the cycle lag between sync SP and this SP
295             ts += sync_lag_cycles * TICKS_PER_CYCLE;
296            
297             if (ts >= TICKS_PER_SECOND * 128L) {
298                 ts -= TICKS_PER_SECOND * 128L;
299             }
300
301 //             m_data_buffer->setBufferHeadTimestamp(ts);
302             int64_t timestamp = ts;
303        
304             // since we have frames_in_buffer frames in the buffer,
305             // we know that the buffer tail lies
306             // frames_in_buffer * rate
307             // later
308             int frames_in_buffer=m_data_buffer->getFrameCounter();
309             timestamp += (int64_t)((float)frames_in_buffer * ticks_per_frame);
310            
311             // this happens when the last timestamp is near wrapping, and
312             // m_framecounter is low.
313             // this means: m_last_timestamp is near wrapping and have just had
314             // a getPackets() from the client side. the projected next_period
315             // boundary lies beyond the wrap value.
316             // the action is to wrap the value.
317             if (timestamp >= TICKS_PER_SECOND * 128L) {
318                 timestamp -= TICKS_PER_SECOND * 128L;
319             }
320        
321             m_data_buffer->setBufferTailTimestamp(timestamp);
322            
323             debugOutput(DEBUG_LEVEL_VERBOSE,"XMIT TS SET: TS=%10lld, TSTMP=%10llu, FC=%4d, %f\n",
324                             ts, timestamp, frames_in_buffer, ticks_per_frame);
325
326         } else {
327             debugOutput(DEBUG_LEVEL_VERY_VERBOSE,"will enable StreamProcessor %p at %u, now is %d\n", this, m_cycle_to_enable_at, cycle);
328         }
329     } else if (m_disabled && !m_is_disabled) {
330         // trying to disable
331         debugOutput(DEBUG_LEVEL_VERBOSE,"disabling StreamProcessor %p at %u\n", this, cycle);
332         m_is_disabled=true;
333     }
334
335     // don't process the stream when it is not enabled, not running
336     // or when the next sample is not due yet.
337    
338     // we do have to generate (semi) valid packets
339     // that means that we'll send NODATA packets.
340     // we don't add payload because DICE devices don't like that.
341     if((until_next>0) || m_is_disabled || !m_running) {
342         // no-data packets have syt=0xFFFF
343         // and have the usual amount of events as dummy data (?)
344         packet->fdf = IEC61883_FDF_NODATA;
345         packet->syt = 0xffff;
346        
347         // the dbc is incremented even with no data packets
348         m_dbc += m_syt_interval;
349
350         // this means no-data packets with payload (DICE doesn't like that)
351         *length = 2*sizeof(quadlet_t) + m_syt_interval * m_dimension * sizeof(quadlet_t);
352        
353         // this means no-data packets without payload
354         //*length = 2*sizeof(quadlet_t);
355        
356         *tag = IEC61883_TAG_WITH_CIP;
357         *sy = 0;
358        
359         return RAW1394_ISO_DEFER;
360     }
361    
362     // construct the packet
363     nevents = m_syt_interval;
364     m_dbc += m_syt_interval;
365    
366     *tag = IEC61883_TAG_WITH_CIP;
367     *sy = 0;
368    
369     if (m_data_buffer->readFrames(nevents, (char *)(data + 8)))
370     {
371         *length = nevents*sizeof(quadlet_t)*m_dimension + 8;
372
373         // process all ports that should be handled on a per-packet base
374         // this is MIDI for AMDTP (due to the need of DBC)
375         if (!encodePacketPorts((quadlet_t *)(data+8), nevents, packet->dbc)) {
376             debugWarning("Problem encoding Packet Ports\n");
377         }
378
379         packet->fdf = m_fdf;
380
381         // convert the timestamp to SYT format
382         uint64_t ts=timestamp + TRANSMIT_TRANSFER_DELAY;
383        
384         // check if it wrapped
385         if (ts >= TICKS_PER_SECOND * 128L) {
386             ts -= TICKS_PER_SECOND * 128L;
387         }
388        
389         unsigned int timestamp_SYT = TICKS_TO_SYT(ts);
390         packet->syt = ntohs(timestamp_SYT);
391        
392         // update the frame counter such that it reflects the new value
393         // done in the SP base class
394 //         if (!StreamProcessor::getFrames(nevents)) {
395 //             debugError("Could not do StreamProcessor::getFrames(%d)\n",nevents);
396 //              return RAW1394_ISO_ERROR;
397 //         }
398        
399         return RAW1394_ISO_OK;   
400     } else {
401         /* there is no more data in the ringbuffer */
402         // convert the timestamp to SYT format
403         uint64_t ts=timestamp + TRANSMIT_TRANSFER_DELAY;
404        
405         // check if it wrapped
406         if (ts >= TICKS_PER_SECOND * 128L) {
407             ts -= TICKS_PER_SECOND * 128L;
408         }
409
410         debugWarning("Transmit buffer underrun (now %d, queue %d, target %d)\n",
411                  now_cycles, cycle, TICKS_TO_CYCLES(ts));
412
413         nevents=0;
414
415         // TODO: we have to be a little smarter here
416         //       because we have some slack on the device side (TRANSFER_DELAY)
417         //       we can allow some skipped packets
418         // signal underrun
419         m_xruns++;
420
421         // disable the processing, will be re-enabled when
422         // the xrun is handled
423         m_disabled=true;
424         m_is_disabled=true;
425
426         // compose a no-data packet, we should always
427         // send a valid packet
428         packet->fdf = IEC61883_FDF_NODATA;
429         packet->syt = 0xffff;
430
431         // this means no-data packets with payload (DICE doesn't like that)
432         *length = 2*sizeof(quadlet_t) + m_syt_interval * m_dimension * sizeof(quadlet_t);
433
434         // this means no-data packets without payload
435         //*length = 2*sizeof(quadlet_t);
436
437         return RAW1394_ISO_DEFER;
438     }
439
440     // we shouldn't get here
441     return RAW1394_ISO_ERROR;
442
443 }
444
445 int64_t AmdtpTransmitStreamProcessor::getTimeUntilNextPeriodUsecs() {
446     debugFatal("IMPLEMENT ME!");
447     return 0;
448 }
449
450 uint64_t AmdtpTransmitStreamProcessor::getTimeAtPeriodUsecs() {
451     // then we should convert this into usecs
452     // FIXME: we assume that the TimeSource of the IsoHandler is
453     //        in usecs.
454     return m_handler->mapToTimeSource(getTimeAtPeriod());
455 }
456
457 uint64_t AmdtpTransmitStreamProcessor::getTimeAtPeriod() {
458     debugFatal("IMPLEMENT ME!");
459    
460     return 0;
461 }
462
463 bool AmdtpTransmitStreamProcessor::prefill() {
464     if(!transferSilence(m_ringbuffer_size_frames)) {
465         debugFatal("Could not prefill transmit stream\n");
466         return false;
467     }
468
469     // when the buffer is prefilled, we should
470     // also initialize the base timestamp
471     // this base timestamp is the timestamp of the
472     // last buffer transfer.
473 //     uint64_t ts;
474 //     uint64_t fc;
475 //     m_SyncSource->m_data_buffer->getBufferHeadTimestamp(&ts, &fc); // thread safe
476
477     // update the frame counter such that it reflects the buffer content,
478     // the buffer tail timestamp is initialized when the SP is enabled
479     // done in the SP base class
480 //     if (!StreamProcessor::putFrames(m_ringbuffer_size_frames, ts)) {
481 //         debugError("Could not do StreamProcessor::putFrames(%d, %011llu)\n",
482 //             m_ringbuffer_size_frames,ts);
483 //         return false;
484 //     }
485
486     return true;
487 }
488
489 bool AmdtpTransmitStreamProcessor::reset() {
490
491     debugOutput( DEBUG_LEVEL_VERBOSE, "Resetting...\n");
492
493     // reset the statistics
494     m_PeriodStat.reset();
495     m_PacketStat.reset();
496     m_WakeupStat.reset();
497    
498     // reset all non-device specific stuff
499     // i.e. the iso stream and the associated ports
500     if(!TransmitStreamProcessor::reset()) {
501         debugFatal("Could not do base class reset\n");
502         return false;
503     }
504    
505     // we should prefill the event buffer
506     if (!prefill()) {
507         debugFatal("Could not prefill buffers\n");
508         return false;   
509     }
510    
511     return true;
512 }
513
514 bool AmdtpTransmitStreamProcessor::prepare() {
515     m_PeriodStat.setName("XMT PERIOD");
516     m_PacketStat.setName("XMT PACKET");
517     m_WakeupStat.setName("XMT WAKEUP");
518
519     debugOutput( DEBUG_LEVEL_VERBOSE, "Preparing...\n");
520    
521     // prepare all non-device specific stuff
522     // i.e. the iso stream and the associated ports
523     if(!TransmitStreamProcessor::prepare()) {
524         debugFatal("Could not prepare base class\n");
525         return false;
526     }
527    
528     switch (m_framerate) {
529     case 32000:
530         m_syt_interval = 8;
531         m_fdf = IEC61883_FDF_SFC_32KHZ;
532         break;
533     case 44100:
534         m_syt_interval = 8;
535         m_fdf = IEC61883_FDF_SFC_44K1HZ;
536         break;
537     default:
538     case 48000:
539         m_syt_interval = 8;
540         m_fdf = IEC61883_FDF_SFC_48KHZ;
541         break;
542     case 88200:
543         m_syt_interval = 16;
544         m_fdf = IEC61883_FDF_SFC_88K2HZ;
545         break;
546     case 96000:
547         m_syt_interval = 16;
548         m_fdf = IEC61883_FDF_SFC_96KHZ;
549         break;
550     case 176400:
551         m_syt_interval = 32;
552         m_fdf = IEC61883_FDF_SFC_176K4HZ;
553         break;
554     case 192000:
555         m_syt_interval = 32;
556         m_fdf = IEC61883_FDF_SFC_192KHZ;
557         break;
558     }
559    
560     iec61883_cip_init (
561         &m_cip_status,
562         IEC61883_FMT_AMDTP,
563         m_fdf,
564         m_framerate,
565         m_dimension,
566         m_syt_interval);
567
568     // prepare the framerate estimate
569     m_ticks_per_frame = (TICKS_PER_SECOND*1.0) / ((float)m_framerate);
570    
571     // allocate the event buffer
572     m_ringbuffer_size_frames=m_nb_buffers * m_period;
573
574     // add the receive processing delay
575 //     m_ringbuffer_size_frames+=(uint)(RECEIVE_PROCESSING_DELAY/m_ticks_per_frame);
576
577     assert(m_data_buffer);   
578     m_data_buffer->setBufferSize(m_ringbuffer_size_frames);
579     m_data_buffer->setEventSize(sizeof(quadlet_t));
580     m_data_buffer->setEventsPerFrame(m_dimension);
581    
582     m_data_buffer->setUpdatePeriod(m_period);
583     m_data_buffer->setNominalRate(m_ticks_per_frame);
584    
585     m_data_buffer->setWrapValue(128L*TICKS_PER_SECOND);
586    
587     m_data_buffer->prepare();
588
589     // set the parameters of ports we can:
590     // we want the audio ports to be period buffered,
591     // and the midi ports to be packet buffered
592     for ( PortVectorIterator it = m_Ports.begin();
593           it != m_Ports.end();
594           ++it )
595     {
596         debugOutput(DEBUG_LEVEL_VERBOSE, "Setting up port %s\n",(*it)->getName().c_str());
597         if(!(*it)->setBufferSize(m_period)) {
598             debugFatal("Could not set buffer size to %d\n",m_period);
599             return false;
600         }
601        
602        
603         switch ((*it)->getPortType()) {
604             case Port::E_Audio:
605                 if(!(*it)->setSignalType(Port::E_PeriodSignalled)) {
606                     debugFatal("Could not set signal type to PeriodSignalling");
607                     return false;
608                 }
609                 debugWarning("---------------- ! Doing hardcoded test setup ! --------------\n");
610                 // buffertype and datatype are dependant on the API
611                 if(!(*it)->setBufferType(Port::E_PointerBuffer)) {
612                     debugFatal("Could not set buffer type");
613                     return false;
614                 }
615                 if(!(*it)->useExternalBuffer(true)) {
616                     debugFatal("Could not set external buffer usage");
617                     return false;
618                 }
619                
620                 if(!(*it)->setDataType(Port::E_Float)) {
621                     debugFatal("Could not set data type");
622                     return false;
623                 }
624                
625                
626                 break;
627             case Port::E_Midi:
628                 if(!(*it)->setSignalType(Port::E_PacketSignalled)) {
629                     debugFatal("Could not set signal type to PeriodSignalling");
630                     return false;
631                 }
632                
633                 // we use a timing unit of 10ns
634                 // this makes sure that for the max syt interval
635                 // we don't have rounding, and keeps the numbers low
636                 // we have 1 slot every 8 events
637                 // we have syt_interval events per packet
638                 // => syt_interval/8 slots per packet
639                 // packet rate is 8000pkt/sec => interval=125us
640                 // so the slot interval is (1/8000)/(syt_interval/8)
641                 // or: 1/(1000 * syt_interval) sec
642                 // which is 1e9/(1000*syt_interval) nsec
643                 // or 100000/syt_interval 'units'
644                 // the event interval is fixed to 320us = 32000 'units'
645                 if(!(*it)->useRateControl(true,(100000/m_syt_interval),32000, false)) {
646                     debugFatal("Could not set signal type to PeriodSignalling");
647                     return false;
648                 }
649                
650                 // buffertype and datatype are dependant on the API
651                 debugWarning("---------------- ! Doing hardcoded test setup ! --------------\n");
652                 // buffertype and datatype are dependant on the API
653                 if(!(*it)->setBufferType(Port::E_RingBuffer)) {
654                     debugFatal("Could not set buffer type");
655                     return false;
656                 }
657                 if(!(*it)->setDataType(Port::E_MidiEvent)) {
658                     debugFatal("Could not set data type");
659                     return false;
660                 }
661                 break;
662             default:
663                 debugWarning("Unsupported port type specified\n");
664                 break;
665         }
666     }
667
668     // the API specific settings of the ports should already be set,
669     // as this is called from the processorManager->prepare()
670     // so we can init the ports
671     if(!initPorts()) {
672         debugFatal("Could not initialize ports!\n");
673         return false;
674     }
675
676     if(!preparePorts()) {
677         debugFatal("Could not initialize ports!\n");
678         return false;
679     }
680    
681     // prefilling is done in ...()
682     // because at that point the streams are running,
683     // while here they are not.
684    
685     // prefill the event buffer
686     // NOTE: do we need to prefill? reset() is called, so everything is prefilled then
687 //     if (!prefill()) {
688 //         debugFatal("Could not prefill buffers\n");
689 //         return false;   
690 //     }
691    
692     debugOutput( DEBUG_LEVEL_VERBOSE, "Prepared for:\n");
693     debugOutput( DEBUG_LEVEL_VERBOSE, " Samplerate: %d, FDF: %d, DBS: %d, SYT: %d\n",
694              m_framerate,m_fdf,m_dimension,m_syt_interval);
695     debugOutput( DEBUG_LEVEL_VERBOSE, " PeriodSize: %d, NbBuffers: %d\n",
696              m_period,m_nb_buffers);
697     debugOutput( DEBUG_LEVEL_VERBOSE, " Port: %d, Channel: %d\n",
698              m_port,m_channel);
699
700     return true;
701
702 }
703
704 bool AmdtpTransmitStreamProcessor::prepareForStart() {
705
706     return true;
707 }
708
709 bool AmdtpTransmitStreamProcessor::prepareForStop() {
710     disable();
711     return true;
712 }
713
714 bool AmdtpTransmitStreamProcessor::prepareForEnable() {
715
716     debugOutput(DEBUG_LEVEL_VERBOSE,"Preparing to enable...\n");
717
718     if (!StreamProcessor::prepareForEnable()) {
719         debugError("StreamProcessor::prepareForEnable failed\n");
720         return false;
721     }
722
723     return true;
724 }
725
726 bool AmdtpTransmitStreamProcessor::transferSilence(unsigned int nframes) {
727     bool retval;
728    
729     char *dummybuffer=(char *)calloc(sizeof(quadlet_t),nframes*m_dimension);
730    
731     transmitSilenceBlock(dummybuffer, nframes, 0);
732
733     // add the silence data to the ringbuffer
734     if(m_data_buffer->writeFrames(nframes, dummybuffer, 0)) {
735         retval=true;
736     } else {
737         debugWarning("Could not write to event buffer\n");
738         retval=false;
739     }
740
741     free(dummybuffer);
742    
743     return retval;
744 }
745
746 bool AmdtpTransmitStreamProcessor::canClientTransferFrames(unsigned int nbframes) {
747     // there has to be enough space to put the frames in
748     return m_ringbuffer_size_frames - m_data_buffer->getFrameCounter() > nbframes;
749 }
750
751 bool AmdtpTransmitStreamProcessor::putFrames(unsigned int nbframes, int64_t ts) {
752     m_PeriodStat.mark(m_data_buffer->getBufferFill());
753    
754     debugOutput(DEBUG_LEVEL_VERY_VERBOSE, "AmdtpTransmitStreamProcessor::putFrames(%d, %llu)\n",nbframes, ts);
755    
756     m_data_buffer->blockProcessWriteFrames(nbframes, ts);
757    
758     // recalculate the buffer tail timestamp
759     float ticks_per_frame=m_SyncSource->getTicksPerFrame();
760    
761     // this makes that the last sample to be sent out on ISO
762     // has the same timestamp as the last one transfered
763     // to the client
764     // plus one frame
765     ts += (uint64_t)ticks_per_frame;
766     int64_t timestamp = ts;
767    
768     // however we have to preserve causality, meaning that we have to make
769     // sure that the worst-case buffer head timestamp still lies in the future.
770     // this worst case timestamp occurs when the xmit buffer is completely full.
771     // therefore we add m_ringbuffer_size_frames * ticks_per_frame to the timestamp.
772     // this will make sure that the buffer head timestamp lies in the future.
773     // the netto effect of this is that the system works as if the buffer processing
774     // by the client doesn't take time.
775    
776     timestamp += (int64_t)((float)m_ringbuffer_size_frames * ticks_per_frame);
777    
778     // wrap the timestamp if nescessary
779     if (timestamp >= TICKS_PER_SECOND * 128L) {
780         timestamp -= TICKS_PER_SECOND * 128L;
781     }
782
783     debugOutput(DEBUG_LEVEL_VERY_VERBOSE, "StreamProcessor::putFrames(%d, %llu)\n",nbframes, timestamp);
784
785     // update the frame counter such that it reflects the new value,
786     // and also update the buffer tail timestamp
787     // done in the SP base class
788 //     if (!StreamProcessor::putFrames(nbframes, timestamp)) {
789 //         debugError("Could not do StreamProcessor::putFrames(%d, %llu)\n",nbframes, timestamp);
790 //         return false;
791 //     }
792
793     return true;
794 }
795 /*
796  * write received events to the stream ringbuffers.
797  */
798
799 bool AmdtpTransmitStreamProcessor::processWriteBlock(char *data,
800                        unsigned int nevents, unsigned int offset)
801 {
802     bool no_problem=true;
803
804     for ( PortVectorIterator it = m_PeriodPorts.begin();
805           it != m_PeriodPorts.end();
806           ++it )
807     {
808
809         if((*it)->isDisabled()) {continue;};
810        
811         //FIXME: make this into a static_cast when not DEBUG?
812
813         AmdtpPortInfo *pinfo=dynamic_cast<AmdtpPortInfo *>(*it);
814         assert(pinfo); // this should not fail!!
815
816         switch(pinfo->getFormat()) {
817         case AmdtpPortInfo::E_MBLA:
818             if(encodePortToMBLAEvents(static_cast<AmdtpAudioPort *>(*it), (quadlet_t *)data, offset, nevents)) {
819                 debugWarning("Could not encode port %s to MBLA events",(*it)->getName().c_str());
820                 no_problem=false;
821             }
822             break;
823         case AmdtpPortInfo::E_SPDIF: // still unimplemented
824             break;
825         default: // ignore
826             break;
827         }
828     }
829     return no_problem;
830
831 }
832
833 int AmdtpTransmitStreamProcessor::transmitSilenceBlock(char *data,
834                        unsigned int nevents, unsigned int offset)
835 {
836     int problem=0;
837
838     for ( PortVectorIterator it = m_PeriodPorts.begin();
839           it != m_PeriodPorts.end();
840           ++it )
841     {
842
843         //FIXME: make this into a static_cast when not DEBUG?
844
845         AmdtpPortInfo *pinfo=dynamic_cast<AmdtpPortInfo *>(*it);
846         assert(pinfo); // this should not fail!!
847
848         switch(pinfo->getFormat()) {
849         case AmdtpPortInfo::E_MBLA:
850             if(encodeSilencePortToMBLAEvents(static_cast<AmdtpAudioPort *>(*it), (quadlet_t *)data, offset, nevents)) {
851                 debugWarning("Could not encode port %s to MBLA events",(*it)->getName().c_str());
852                 problem=1;
853             }
854             break;
855         case AmdtpPortInfo::E_SPDIF: // still unimplemented
856             break;
857         default: // ignore
858             break;
859         }
860     }
861     return problem;
862
863 }
864
865 /**
866  * @brief decode a packet for the packet-based ports
867  *
868  * @param data Packet data
869  * @param nevents number of events in data (including events of other ports & port types)
870  * @param dbc DataBlockCount value for this packet
871  * @return true if all successfull
872  */
873 bool AmdtpTransmitStreamProcessor::encodePacketPorts(quadlet_t *data, unsigned int nevents, unsigned int dbc)
874 {
875     bool ok=true;
876     char byte;
877    
878     quadlet_t *target_event=NULL;
879     unsigned int j;
880    
881     for ( PortVectorIterator it = m_PacketPorts.begin();
882           it != m_PacketPorts.end();
883           ++it )
884     {
885
886 #ifdef DEBUG
887         AmdtpPortInfo *pinfo=dynamic_cast<AmdtpPortInfo *>(*it);
888         assert(pinfo); // this should not fail!!
889
890         // the only packet type of events for AMDTP is MIDI in mbla
891         assert(pinfo->getFormat()==AmdtpPortInfo::E_Midi);
892 #endif
893        
894         AmdtpMidiPort *mp=static_cast<AmdtpMidiPort *>(*it);
895        
896         // we encode this directly (no function call) due to the high frequency
897         /* idea:
898         spec says: current_midi_port=(dbc+j)%8;
899         => if we start at (dbc+stream->location-1)%8 [due to location_min=1],
900         we'll start at the right event for the midi port.
901         => if we increment j with 8, we stay at the right event.
902         */
903         // FIXME: as we know in advance how big a packet is (syt_interval) we can
904         //        predict how much loops will be present here
905         // first prefill the buffer with NO_DATA's on all time muxed channels
906        
907         for(j = (dbc & 0x07)+mp->getLocation()-1; j < nevents; j += 8) {
908        
909             target_event=(quadlet_t *)(data + ((j * m_dimension) + mp->getPosition()));
910            
911             if(mp->canRead()) { // we can send a byte
912                 mp->readEvent(&byte);
913                 *target_event=htonl(
914                     IEC61883_AM824_SET_LABEL((byte)<<16,
915                                              IEC61883_AM824_LABEL_MIDI_1X));
916             } else {
917                 // can't send a byte, either because there is no byte,
918                 // or because this would exceed the maximum rate
919                 *target_event=htonl(
920                     IEC61883_AM824_SET_LABEL(0,IEC61883_AM824_LABEL_MIDI_NO_DATA));
921             }
922         }
923
924     }
925        
926     return ok;
927 }
928
929
930 int AmdtpTransmitStreamProcessor::encodePortToMBLAEvents(AmdtpAudioPort *p, quadlet_t *data,
931                        unsigned int offset, unsigned int nevents)
932 {
933     unsigned int j=0;
934
935     quadlet_t *target_event;
936
937     target_event=(quadlet_t *)(data + p->getPosition());
938
939     switch(p->getDataType()) {
940         default:
941         case Port::E_Int24:
942             {
943                 quadlet_t *buffer=(quadlet_t *)(p->getBufferAddress());
944
945                 assert(nevents + offset <= p->getBufferSize());
946
947                 buffer+=offset;
948
949                 for(j = 0; j < nevents; j += 1) { // decode max nsamples
950                     *target_event = htonl((*(buffer) & 0x00FFFFFF) | 0x40000000);
951                     buffer++;
952                     target_event += m_dimension;
953                 }
954             }
955             break;
956         case Port::E_Float:
957             {
958                 const float multiplier = (float)(0x7FFFFF00);
959                 float *buffer=(float *)(p->getBufferAddress());
960
961                 assert(nevents + offset <= p->getBufferSize());
962
963                 buffer+=offset;
964
965                 for(j = 0; j < nevents; j += 1) { // decode max nsamples               
966    
967                     // don't care for overflow
968                     float v = *buffer * multiplier;  // v: -231 .. 231
969                     unsigned int tmp = ((int)v);
970                     *target_event = htonl((tmp >> 8) | 0x40000000);
971                    
972                     buffer++;
973                     target_event += m_dimension;
974                 }
975             }
976             break;
977     }
978
979     return 0;
980 }
981 int AmdtpTransmitStreamProcessor::encodeSilencePortToMBLAEvents(AmdtpAudioPort *p, quadlet_t *data,
982                        unsigned int offset, unsigned int nevents)
983 {
984     unsigned int j=0;
985
986     quadlet_t *target_event;
987
988     target_event=(quadlet_t *)(data + p->getPosition());
989
990     switch(p->getDataType()) {
991         default:
992         case Port::E_Int24:
993         case Port::E_Float:
994             {
995                 for(j = 0; j < nevents; j += 1) { // decode max nsamples
996                     *target_event = htonl(0x40000000);
997                     target_event += m_dimension;
998                 }
999             }
1000             break;
1001     }
1002
1003     return 0;
1004 }
1005
1006 /* --------------------- RECEIVE ----------------------- */
1007
1008 AmdtpReceiveStreamProcessor::AmdtpReceiveStreamProcessor(int port, int framerate, int dimension)
1009     : ReceiveStreamProcessor(port, framerate), m_dimension(dimension), m_last_timestamp(0), m_last_timestamp2(0) {
1010
1011 }
1012
1013 AmdtpReceiveStreamProcessor::~AmdtpReceiveStreamProcessor() {
1014
1015 }
1016
1017 bool AmdtpReceiveStreamProcessor::init() {
1018
1019     // call the parent init
1020     // this has to be done before allocating the buffers,
1021     // because this sets the buffersizes from the processormanager
1022     if(!ReceiveStreamProcessor::init()) {
1023         debugFatal("Could not do base class init (%d)\n",this);
1024         return false;
1025     }
1026
1027     return true;
1028 }
1029
1030 enum raw1394_iso_disposition
1031 AmdtpReceiveStreamProcessor::putPacket(unsigned char *data, unsigned int length,
1032                   unsigned char channel, unsigned char tag, unsigned char sy,
1033                   unsigned int cycle, unsigned int dropped) {
1034    
1035     enum raw1394_iso_disposition retval=RAW1394_ISO_OK;
1036     m_last_cycle=cycle;
1037    
1038     struct iec61883_packet *packet = (struct iec61883_packet *) data;
1039     assert(packet);
1040
1041 #ifdef DEBUG
1042     if(dropped>0) {
1043         debugWarning("Dropped %d packets on cycle %d\n",dropped, cycle);
1044     }
1045 #endif
1046
1047     debugOutput(DEBUG_LEVEL_VERY_VERBOSE,"ch%2u: CY=%4u, SYT=%08X (%4ucy + %04uticks) (running=%d, disabled=%d,%d)\n",
1048         channel, cycle,ntohs(packet->syt), 
1049         CYCLE_TIMER_GET_CYCLES(ntohs(packet->syt)), CYCLE_TIMER_GET_OFFSET(ntohs(packet->syt)),
1050         m_running,m_disabled,m_is_disabled);
1051
1052     if((packet->fmt == 0x10) && (packet->fdf != 0xFF) && (packet->syt != 0xFFFF) && (packet->dbs>0) && (length>=2*sizeof(quadlet_t))) {
1053         unsigned int nevents=((length / sizeof (quadlet_t)) - 2)/packet->dbs;
1054
1055         //=> store the previous timestamp
1056         m_last_timestamp2=m_last_timestamp;
1057
1058         //=> convert the SYT to ticks
1059         unsigned int syt_timestamp=ntohs(packet->syt);
1060
1061         debugOutput(DEBUG_LEVEL_VERY_VERBOSE,"ch%2u: CY=%4u, SYT=%08X (%4u cycles + %04u ticks), FC=%04d, %d\n",
1062             channel, cycle,syt_timestamp, 
1063             CYCLE_TIMER_GET_CYCLES(syt_timestamp), CYCLE_TIMER_GET_OFFSET(syt_timestamp),
1064             m_data_buffer->getFrameCounter(), m_is_disabled);
1065        
1066         // reconstruct the full cycle
1067         unsigned int cc=m_handler->getCycleTimer();
1068         unsigned int cc_cycles=CYCLE_TIMER_GET_CYCLES(cc);
1069         unsigned int cc_seconds=CYCLE_TIMER_GET_SECS(cc);
1070        
1071         // the cycletimer has wrapped since this packet was received
1072         // we want cc_seconds to reflect the 'seconds' at the point this
1073         // was received
1074         if (cycle>cc_cycles) {
1075             if (cc_seconds) {
1076                 cc_seconds--;
1077             } else {
1078                 // seconds has wrapped around, so we'd better not substract 1
1079                 // the good value is 127
1080                 cc_seconds=127;
1081             }
1082         }
1083        
1084         // reconstruct the top part of the timestamp using the current cycle number
1085         unsigned int now_cycle_masked=cycle & 0xF;
1086         unsigned int syt_cycle=CYCLE_TIMER_GET_CYCLES(syt_timestamp);
1087        
1088         // if this is true, wraparound has occurred, undo this wraparound
1089         if(syt_cycle<now_cycle_masked) syt_cycle += 0x10;
1090        
1091         // this is the difference in cycles wrt the cycle the
1092         // timestamp was received
1093         unsigned int delta_cycles=syt_cycle-now_cycle_masked;
1094        
1095         // reconstruct the cycle part of the timestamp
1096         unsigned int new_cycles=cycle + delta_cycles;
1097        
1098         // if the cycles cause a wraparound of the cycle timer,
1099         // perform this wraparound
1100         // and convert the timestamp into ticks
1101         if(new_cycles<8000) {
1102             m_last_timestamp  = new_cycles * TICKS_PER_CYCLE;
1103         } else {
1104             debugOutput(DEBUG_LEVEL_VERY_VERBOSE,
1105                 "Detected wraparound: %d + %d = %d\n",
1106                 cycle,delta_cycles,new_cycles);
1107            
1108             new_cycles-=8000; // wrap around
1109             m_last_timestamp  = new_cycles * TICKS_PER_CYCLE;
1110             // add one second due to wraparound
1111             m_last_timestamp += TICKS_PER_SECOND;
1112         }
1113        
1114         m_last_timestamp += CYCLE_TIMER_GET_OFFSET(syt_timestamp);
1115         m_last_timestamp += cc_seconds * TICKS_PER_SECOND;
1116        
1117         // we have to keep in mind that there are also
1118         // some packets buffered by the ISO layer
1119         // at most x=m_handler->getWakeupInterval()
1120         // these contain at most x*syt_interval
1121         // frames, meaning that we might receive
1122         // this packet x*syt_interval*ticks_per_frame
1123         // later than expected (the real receive time)
1124         debugOutput(DEBUG_LEVEL_VERY_VERBOSE,"STMP: %lluticks | buff=%d, syt_interval=%d, tpf=%f\n",
1125             m_last_timestamp, m_handler->getWakeupInterval(),m_syt_interval,m_ticks_per_frame);
1126        
1127         m_last_timestamp += (uint64_t)(((float)m_handler->getWakeupInterval())
1128                                        * ((float)m_syt_interval) * m_ticks_per_frame);
1129         debugOutput(DEBUG_LEVEL_VERY_VERBOSE," ==> %lluticks\n", m_last_timestamp);
1130        
1131         // the receive processing delay indicates how much
1132         // extra time we need as slack
1133         m_last_timestamp += RECEIVE_PROCESSING_DELAY;
1134        
1135         // wrap if nescessary
1136         if (m_last_timestamp >= TICKS_PER_SECOND * 128L) {
1137             m_last_timestamp -= TICKS_PER_SECOND * 128L;
1138         }
1139        
1140         //=> now estimate the device frame rate
1141         if (m_last_timestamp2 && m_last_timestamp) {
1142             // try and estimate the frame rate from the device
1143            
1144             // first get the measured difference between both
1145             // timestamps
1146             int64_t measured_difference;
1147             measured_difference=((int64_t)(m_last_timestamp))
1148                                -((int64_t)(m_last_timestamp2));
1149             // correct for seconds wraparound
1150             if (m_last_timestamp<m_last_timestamp2) {
1151                 measured_difference+=128L*TICKS_PER_SECOND;
1152             }
1153
1154             // implement a 1st order DLL to estimate the framerate
1155             // this is the number of ticks between two samples
1156             float f=measured_difference;
1157             float err = f / (1.0*m_syt_interval) - m_ticks_per_frame;
1158            
1159             debugOutput(DEBUG_LEVEL_VERY_VERBOSE,"SYT: %08X | STMP: %lluticks | DLL: in=%f, current=%f, err=%e\n",syt_timestamp, m_last_timestamp, f,m_ticks_per_frame,err);
1160
1161 #ifdef DEBUG
1162             // this helps to detect wraparound issues
1163             if(f > 1.5*((TICKS_PER_SECOND*1.0) / m_framerate)*m_syt_interval) {
1164                 debugWarning("Timestamp diff more than 50%% of the nominal diff too large!\n");
1165                 debugWarning(" SYT: %08X | STMP: %llu,%llu | DLL: in=%f, current=%f, err=%e\n",syt_timestamp, m_last_timestamp, m_last_timestamp2, f,m_ticks_per_frame,err);
1166                 debugWarning(" CC: %08X | CC_CY: %u | CC_SEC: %u | SYT_CY: %u | NEW_CY: %u\n",
1167                     cc, cc_cycles, cc_seconds, syt_cycle,new_cycles);
1168                
1169             }
1170             if(f < 0.5*((TICKS_PER_SECOND*1.0) / m_framerate)*m_syt_interval) {
1171                 debugWarning("Timestamp diff more than 50%% of the nominal diff too small!\n");
1172                 debugWarning(" SYT: %08X | STMP: %llu,%llu | DLL: in=%f, current=%f, err=%e\n",syt_timestamp, m_last_timestamp, m_last_timestamp2, f,m_ticks_per_frame,err);
1173             }
1174 #endif
1175             // integrate the error
1176             m_ticks_per_frame += RECEIVE_DLL_INTEGRATION_COEFFICIENT*err;
1177            
1178         }
1179        
1180          debugOutput(DEBUG_LEVEL_VERY_VERBOSE,"R-SYT for cycle (%2d %2d)=>%2d: %5uT (%04uC + %04uT) %04X %04X %d\n",
1181             cycle,now_cycle_masked,delta_cycles,
1182             (m_last_timestamp),
1183             TICKS_TO_CYCLES(m_last_timestamp),
1184             TICKS_TO_OFFSET(m_last_timestamp),
1185             ntohs(packet->syt),TICKS_TO_CYCLE_TIMER(m_last_timestamp)&0xFFFF, dropped
1186          );
1187
1188         //=> signal that we're running (if we are)
1189         if(!m_running && nevents && m_last_timestamp2 && m_last_timestamp) {
1190             debugOutput(DEBUG_LEVEL_VERBOSE,"Receive StreamProcessor %p started running at %d\n", this, cycle);
1191             m_running=true;
1192         }
1193
1194         //=> don't process the stream samples when it is not enabled.
1195         if (!m_disabled && m_is_disabled) {
1196             // this means that we are trying to enable
1197             if (cycle == m_cycle_to_enable_at) {
1198                 m_is_disabled=false;
1199                 debugOutput(DEBUG_LEVEL_VERBOSE,"enabling StreamProcessor %p at %d\n", this, cycle);
1200                 // the previous timestamp is the one we need to start with
1201                 // because we're going to update the buffer again this loop
1202                 m_data_buffer->setBufferTailTimestamp(m_last_timestamp2);
1203                
1204             } else {
1205                 debugOutput(DEBUG_LEVEL_VERY_VERBOSE,"will enable StreamProcessor %p at %u, now is %d\n", this, m_cycle_to_enable_at, cycle);
1206             }
1207         } else if (m_disabled && !m_is_disabled) {
1208             // trying to disable
1209             debugOutput(DEBUG_LEVEL_VERBOSE,"disabling StreamProcessor %p at %u\n", this, cycle);
1210             m_is_disabled=true;
1211         }
1212        
1213         if(m_is_disabled) {
1214
1215             // we keep track of the timestamp here
1216             // this makes sure that we will have a somewhat accurate
1217             // estimate as to when a period might be ready. i.e. it will not
1218             // be ready earlier than this timestamp + period time
1219            
1220             // the next (possible) sample is not this one, but lies
1221             // SYT_INTERVAL * rate later
1222             uint64_t ts=m_last_timestamp+(uint64_t)((float)m_syt_interval * m_ticks_per_frame);
1223            
1224             // wrap if nescessary
1225             if (ts >= TICKS_PER_SECOND * 128L) {
1226                 ts -= TICKS_PER_SECOND * 128L;
1227             }
1228             // set the timestamps
1229             m_data_buffer->setBufferTailTimestamp(ts);
1230            
1231             return RAW1394_ISO_DEFER;
1232         }
1233        
1234         //=> process the packet
1235         // add the data payload to the ringbuffer
1236         if(m_data_buffer->writeFrames(nevents, (char *)(data+8), m_last_timestamp)) {
1237             retval=RAW1394_ISO_OK;
1238            
1239             // process all ports that should be handled on a per-packet base
1240             // this is MIDI for AMDTP (due to the need of DBC)
1241             if (!decodePacketPorts((quadlet_t *)(data+8), nevents, packet->dbc)) {
1242                 debugWarning("Problem decoding Packet Ports\n");
1243                 retval=RAW1394_ISO_DEFER;
1244             }
1245            
1246         } else {
1247        
1248             debugWarning("Receive buffer overrun (cycle %d, FC=%d, PC=%d)\n",
1249                  cycle, m_data_buffer->getFrameCounter(), m_handler->getPacketCount());
1250            
1251             m_xruns++;
1252            
1253             // disable the processing, will be re-enabled when
1254             // the xrun is handled
1255             m_disabled=true;
1256             m_is_disabled=true;
1257
1258             retval=RAW1394_ISO_DEFER;
1259            
1260         }
1261
1262 #ifdef DEBUG
1263         if(packet->dbs) {
1264             debugOutput(DEBUG_LEVEL_VERY_VERBOSE,
1265                 "RCV %04d: CH = %d, FDF = %X. SYT = %6d, DBS = %3d, DBC = %3d, FMT = %3d, LEN = %4d (%2d)\n",
1266                 cycle, channel, packet->fdf,
1267                 packet->syt,
1268                 packet->dbs,
1269                 packet->dbc,
1270                 packet->fmt,
1271                 length,
1272                 ((length / sizeof (quadlet_t)) - 2)/packet->dbs);
1273         }
1274 #endif
1275
1276         // update the frame counter such that it reflects the new value,
1277         // and also update the buffer tail timestamp, as we add new frames
1278         // done in the SP base class
1279 //         if (!StreamProcessor::putFrames(nevents, m_last_timestamp)) {
1280 //             debugError("Could not do StreamProcessor::putFrames(%d, %llu)\n",nevents, m_last_timestamp);
1281 //             return RAW1394_ISO_ERROR;
1282 //         }
1283
1284     }
1285    
1286     return retval;
1287 }
1288
1289 int64_t AmdtpReceiveStreamProcessor::getTimeUntilNextPeriodUsecs() {
1290     uint64_t time_at_period=getTimeAtPeriod();
1291    
1292     uint64_t cycle_timer=m_handler->getCycleTimerTicks();
1293    
1294     int64_t until_next=time_at_period-cycle_timer;
1295    
1296     // the maximal difference we can allow (64secs)
1297     const int64_t max=TICKS_PER_SECOND*64L;
1298    
1299     debugOutput(DEBUG_LEVEL_VERY_VERBOSE, "=> TAP=%11llu, CTR=%11llu, UTN=%11lld, TPUS=%f\n",
1300         time_at_period, cycle_timer, until_next, m_handler->getTicksPerUsec()
1301         );
1302        
1303     if(until_next > max) {
1304         // this means that cycle_timer has wrapped, but
1305         // time_at_period has not. we should unwrap cycle_timer
1306         // by adding TICKS_PER_SECOND*128L, meaning that we should substract
1307         // this value from until_next           
1308         until_next -= TICKS_PER_SECOND*128L;
1309     } else if (until_next < -max) {
1310         // this means that time_at_period has wrapped, but
1311         // cycle_timer has not. we should unwrap time_at_period
1312         // by adding TICKS_PER_SECOND*128L, meaning that we should add
1313         // this value from until_next
1314         until_next += TICKS_PER_SECOND*128L;
1315     }
1316    
1317     debugOutput(DEBUG_LEVEL_VERY_VERBOSE, "   TAP=%11llu, CTR=%11llu, UTN=%11lld, TPUS=%f\n",
1318         time_at_period, cycle_timer, until_next, m_handler->getTicksPerUsec()
1319         );
1320    
1321     // now convert to usecs
1322     // don't use the mapping function because it only works
1323     // for absolute times, not the relative time we are
1324     // using here (which can also be negative).
1325     return (int64_t)(((float)until_next) / m_handler->getTicksPerUsec());
1326 }
1327
1328 uint64_t AmdtpReceiveStreamProcessor::getTimeAtPeriodUsecs() {
1329     // then we should convert this into usecs
1330     // FIXME: we assume that the TimeSource of the IsoHandler is
1331     //        in usecs.
1332     return m_handler->mapToTimeSource(getTimeAtPeriod());
1333 }
1334
1335 uint64_t AmdtpReceiveStreamProcessor::getTimeAtPeriod() {
1336
1337     // every time a packet is received both the framecounter and the base
1338     // timestamp are updated. This means that at any instance of time, the
1339     // front of the buffer (latest sample) timestamp is known.
1340     // As we know the number of frames in the buffer, and we now the rate
1341     // in ticks/frame, we can calculate the back of buffer timestamp as:
1342     //    back_of_buffer_time = front_time - nbframes * rate
1343     // the next period boundary time lies m_period frames later:
1344     //    next_period_boundary = back_of_buffer_time + m_period * rate
1345    
1346     // NOTE: we should account for the fact that the timestamp is not for
1347     //       the latest sample, but for the latest sample minus syt_interval-1
1348     //       because it is the timestamp for the first sample in the packet,
1349     //       while the complete packet contains SYT_INTERVAL samples.
1350     //       this makes the equation:
1351     //          back_of_buffer_time = front_time - (nbframes - (syt_interval - 1)) * rate
1352     //          next_period_boundary = back_of_buffer_time + m_period * rate
1353
1354     // NOTE: where do we add the processing delay?
1355     //       if we add it here:
1356     //          next_period_boundary += RECEIVE_PROCESSING_DELAY
1357    
1358     // the complete equation now is:
1359     // next_period_boundary = front_time - (nbframes - (syt_interval - 1)) * rate
1360     //                        + m_period * rate + RECEIVE_PROCESSING_DELAY
1361     // since syt_interval is a constant value, we can equally well ignore it, as
1362     // if it were already included in RECEIVE_PROCESSING_DELAY
1363     // making the equation (simplified:
1364     // next_period_boundary = front_time + (-nbframes + m_period) * rate
1365     //                        + RECEIVE_PROCESSING_DELAY
1366     // currently this is in ticks
1367    
1368     int64_t fc=m_data_buffer->getFrameCounter();
1369    
1370     int64_t next_period_boundary =  m_last_timestamp;
1371     next_period_boundary     += (int64_t)(((int64_t)m_period
1372                                           - fc) * m_ticks_per_frame);
1373    
1374     debugOutput(DEBUG_LEVEL_VERY_VERBOSE, "=> NPD=%11lld, LTS=%11llu, FC=%5d, TPF=%f\n",
1375         next_period_boundary, m_last_timestamp, fc, m_ticks_per_frame
1376         );
1377    
1378     // this happens if the timestamp wraps around while there are a lot of
1379     // frames in the buffer. We should add the wraparound value of the ticks
1380     // counter
1381     if (next_period_boundary < 0) {
1382         next_period_boundary += TICKS_PER_SECOND * 128L;
1383     }
1384     // this happens when the last timestamp is near wrapping, and
1385     // m_framecounter is low.
1386     // this means: m_last_timestamp is near wrapping and have just had
1387     // a getPackets() from the client side. the projected next_period
1388     // boundary lies beyond the wrap value.
1389     // the action is to wrap the value.
1390     else if (next_period_boundary >= TICKS_PER_SECOND * 128L) {
1391         next_period_boundary -= TICKS_PER_SECOND * 128L;
1392     }
1393    
1394     debugOutput(DEBUG_LEVEL_VERY_VERBOSE, "   NPD=%11lld, LTS=%11llu, FC=%5d, TPF=%f\n",
1395         next_period_boundary, m_last_timestamp, fc, m_ticks_per_frame
1396         );
1397
1398     return next_period_boundary;
1399 }
1400
1401 void AmdtpReceiveStreamProcessor::dumpInfo()
1402 {
1403
1404     StreamProcessor::dumpInfo();
1405    
1406         debugOutputShort( DEBUG_LEVEL_NORMAL, "  Device framerate  : %f\n", 24576000.0/m_ticks_per_frame);
1407
1408 }
1409
1410
1411 void AmdtpReceiveStreamProcessor::setVerboseLevel(int l) {
1412         setDebugLevel(l);
1413         ReceiveStreamProcessor::setVerboseLevel(l);
1414
1415 }
1416
1417 bool AmdtpReceiveStreamProcessor::reset() {
1418
1419     debugOutput( DEBUG_LEVEL_VERBOSE, "Resetting...\n");
1420
1421     m_PeriodStat.reset();
1422     m_PacketStat.reset();
1423     m_WakeupStat.reset();
1424    
1425     // this needs to be reset to the nominal value
1426     // because xruns can cause the DLL value to shift a lot
1427     // making that we run into problems when trying to re-enable
1428     // streaming
1429     m_ticks_per_frame = (TICKS_PER_SECOND*1.0) / ((float)m_framerate);
1430
1431     // reset all non-device specific stuff
1432     // i.e. the iso stream and the associated ports
1433     if(!ReceiveStreamProcessor::reset()) {
1434             debugFatal("Could not do base class reset\n");
1435             return false;
1436     }
1437     return true;
1438 }
1439
1440 bool AmdtpReceiveStreamProcessor::prepare() {
1441
1442     m_PeriodStat.setName("RCV PERIOD");
1443     m_PacketStat.setName("RCV PACKET");
1444     m_WakeupStat.setName("RCV WAKEUP");
1445
1446         // prepare all non-device specific stuff
1447         // i.e. the iso stream and the associated ports
1448         if(!ReceiveStreamProcessor::prepare()) {
1449                 debugFatal("Could not prepare base class\n");
1450                 return false;
1451         }
1452        
1453         debugOutput( DEBUG_LEVEL_VERBOSE, "Preparing...\n");
1454         switch (m_framerate) {
1455         case 32000:
1456                 m_syt_interval = 8;
1457                 break;
1458         case 44100:
1459                 m_syt_interval = 8;
1460                 break;
1461         default:
1462         case 48000:
1463                 m_syt_interval = 8;
1464                 break;
1465         case 88200:
1466                 m_syt_interval = 16;
1467                 break;
1468         case 96000:
1469                 m_syt_interval = 16;
1470                 break;
1471         case 176400:
1472                 m_syt_interval = 32;
1473                 break;
1474         case 192000:
1475                 m_syt_interval = 32;
1476                 break;
1477         }
1478
1479     // prepare the framerate estimate
1480     m_ticks_per_frame = (TICKS_PER_SECOND*1.0) / ((float)m_framerate);
1481
1482     debugOutput(DEBUG_LEVEL_VERBOSE,"Initializing remote ticks/frame to %f\n",m_ticks_per_frame);
1483
1484     // allocate the event buffer
1485     unsigned int ringbuffer_size_frames=m_nb_buffers * m_period;
1486    
1487     // add the processing delay
1488     debugOutput(DEBUG_LEVEL_VERBOSE,"Adding %u frames of SYT slack buffering...\n",
1489         (uint)(RECEIVE_PROCESSING_DELAY/m_ticks_per_frame));
1490     ringbuffer_size_frames+=(uint)(RECEIVE_PROCESSING_DELAY/m_ticks_per_frame);
1491    
1492     assert(m_data_buffer);   
1493     m_data_buffer->setBufferSize(ringbuffer_size_frames);
1494     m_data_buffer->setEventSize(sizeof(quadlet_t));
1495     m_data_buffer->setEventsPerFrame(m_dimension);
1496        
1497     // the buffer is written every syt_interval
1498     m_data_buffer->setUpdatePeriod(m_syt_interval);
1499     m_data_buffer->setNominalRate(m_ticks_per_frame);
1500    
1501     m_data_buffer->setWrapValue(128L*TICKS_PER_SECOND);
1502    
1503     m_data_buffer->prepare();
1504
1505         // set the parameters of ports we can:
1506         // we want the audio ports to be period buffered,
1507         // and the midi ports to be packet buffered
1508         for ( PortVectorIterator it = m_Ports.begin();
1509                   it != m_Ports.end();
1510                   ++it )
1511         {
1512                 debugOutput(DEBUG_LEVEL_VERBOSE, "Setting up port %s\n",(*it)->getName().c_str());
1513                 if(!(*it)->setBufferSize(m_period)) {
1514                         debugFatal("Could not set buffer size to %d\n",m_period);
1515                         return false;
1516                 }
1517
1518                 switch ((*it)->getPortType()) {
1519                         case Port::E_Audio:
1520                                 if(!(*it)->setSignalType(Port::E_PeriodSignalled)) {
1521                                         debugFatal("Could not set signal type to PeriodSignalling");
1522                                         return false;
1523                                 }
1524                                 // buffertype and datatype are dependant on the API
1525                                 debugWarning("---------------- ! Doing hardcoded dummy setup ! --------------\n");
1526                                 // buffertype and datatype are dependant on the API
1527                                 if(!(*it)->setBufferType(Port::E_PointerBuffer)) {
1528                                         debugFatal("Could not set buffer type");
1529                                         return false;
1530                                 }
1531                                 if(!(*it)->useExternalBuffer(true)) {
1532                                         debugFatal("Could not set external buffer usage");
1533                                         return false;
1534                                 }
1535                                 if(!(*it)->setDataType(Port::E_Float)) {
1536                                         debugFatal("Could not set data type");
1537                                         return false;
1538                                 }
1539                                 break;
1540                         case Port::E_Midi:
1541                                 if(!(*it)->setSignalType(Port::E_PacketSignalled)) {
1542                                         debugFatal("Could not set signal type to PacketSignalling");
1543                                         return false;
1544                                 }
1545                                 // buffertype and datatype are dependant on the API
1546                                 // buffertype and datatype are dependant on the API
1547                                 debugWarning("---------------- ! Doing hardcoded test setup ! --------------\n");
1548                                 // buffertype and datatype are dependant on the API
1549                                 if(!(*it)->setBufferType(Port::E_RingBuffer)) {
1550                                         debugFatal("Could not set buffer type");
1551                                         return false;
1552                                 }
1553                                 if(!(*it)->setDataType(Port::E_MidiEvent)) {
1554                                         debugFatal("Could not set data type");
1555                                         return false;
1556                                 }
1557                                 break;
1558                         default:
1559                                 debugWarning("Unsupported port type specified\n");
1560                                 break;
1561                 }
1562
1563         }
1564
1565         // the API specific settings of the ports should already be set,
1566         // as this is called from the processorManager->prepare()
1567         // so we can init the ports
1568         if(!initPorts()) {
1569                 debugFatal("Could not initialize ports!\n");
1570                 return false;
1571         }
1572
1573         if(!preparePorts()) {
1574                 debugFatal("Could not initialize ports!\n");
1575                 return false;
1576         }
1577
1578
1579         debugOutput( DEBUG_LEVEL_VERBOSE, "Prepared for:\n");
1580         debugOutput( DEBUG_LEVEL_VERBOSE, " Samplerate: %d, DBS: %d, SYT: %d\n",
1581                      m_framerate,m_dimension,m_syt_interval);
1582         debugOutput( DEBUG_LEVEL_VERBOSE, " PeriodSize: %d, NbBuffers: %d\n",
1583                      m_period,m_nb_buffers);
1584         debugOutput( DEBUG_LEVEL_VERBOSE, " Port: %d, Channel: %d\n",
1585                      m_port,m_channel);
1586         return true;
1587
1588 }
1589
1590 bool AmdtpReceiveStreamProcessor::prepareForStart() {
1591     disable();
1592     return true;
1593 }
1594
1595 bool AmdtpReceiveStreamProcessor::prepareForStop() {
1596     disable();
1597     return true;
1598 }
1599
1600 bool AmdtpReceiveStreamProcessor::canClientTransferFrames(unsigned int nbframes) {
1601     return m_data_buffer->getFrameCounter() >= (int) nbframes;
1602 }
1603
1604 bool AmdtpReceiveStreamProcessor::getFrames(unsigned int nbframes) {
1605
1606     m_PeriodStat.mark(m_data_buffer->getBufferFill());
1607
1608     // ask the buffer to process nbframes of frames
1609     // using it's registered client's processReadBlock(),
1610     // which should be ours
1611     m_data_buffer->blockProcessReadFrames(nbframes);
1612
1613     // update the frame counter such that it reflects the new value,
1614     // done in the SP base class
1615 /*   
1616     if (!StreamProcessor::getFrames(nbframes)) {
1617         debugError("Could not do StreamProcessor::getFrames(%d)\n", nbframes);
1618         return false;
1619     }*/
1620
1621     return true;
1622 }
1623
1624 /**
1625  * \brief write received events to the stream ringbuffers.
1626  */
1627 bool AmdtpReceiveStreamProcessor::processReadBlock(char *data,
1628                                            unsigned int nevents, unsigned int offset)
1629 {
1630         debugOutput( DEBUG_LEVEL_VERY_VERBOSE, "(%p)->processReadBlock(%u, %u)\n",this,nevents,offset);
1631        
1632         bool no_problem=true;
1633
1634         for ( PortVectorIterator it = m_PeriodPorts.begin();
1635           it != m_PeriodPorts.end();
1636           ++it )
1637     {
1638
1639         if((*it)->isDisabled()) {continue;};
1640
1641                 //FIXME: make this into a static_cast when not DEBUG?
1642
1643                 AmdtpPortInfo *pinfo=dynamic_cast<AmdtpPortInfo *>(*it);
1644                 assert(pinfo); // this should not fail!!
1645
1646                 switch(pinfo->getFormat()) {
1647                 case AmdtpPortInfo::E_MBLA:
1648                         if(decodeMBLAEventsToPort(static_cast<AmdtpAudioPort *>(*it), (quadlet_t *)data, offset, nevents)) {
1649                                 debugWarning("Could not decode packet MBLA to port %s",(*it)->getName().c_str());
1650                                 no_problem=false;
1651                         }
1652                         break;
1653                 case AmdtpPortInfo::E_SPDIF: // still unimplemented
1654                         break;
1655         /* for this processor, midi is a packet based port
1656                 case AmdtpPortInfo::E_Midi:
1657                         break;*/
1658                 default: // ignore
1659                         break;
1660                 }
1661     }
1662     return no_problem;
1663
1664 }
1665
1666 /**
1667  * @brief decode a packet for the packet-based ports
1668  *
1669  * @param data Packet data
1670  * @param nevents number of events in data (including events of other ports & port types)
1671  * @param dbc DataBlockCount value for this packet
1672  * @return true if all successfull
1673  */
1674 bool AmdtpReceiveStreamProcessor::decodePacketPorts(quadlet_t *data, unsigned int nevents, unsigned int dbc)
1675 {
1676         bool ok=true;
1677        
1678         quadlet_t *target_event=NULL;
1679         unsigned int j;
1680        
1681         for ( PortVectorIterator it = m_PacketPorts.begin();
1682           it != m_PacketPorts.end();
1683           ++it )
1684         {
1685
1686 #ifdef DEBUG
1687                 AmdtpPortInfo *pinfo=dynamic_cast<AmdtpPortInfo *>(*it);
1688                 assert(pinfo); // this should not fail!!
1689
1690                 // the only packet type of events for AMDTP is MIDI in mbla
1691                 assert(pinfo->getFormat()==AmdtpPortInfo::E_Midi);
1692 #endif
1693                 AmdtpMidiPort *mp=static_cast<AmdtpMidiPort *>(*it);
1694                
1695                 // we decode this directly (no function call) due to the high frequency
1696                 /* idea:
1697                 spec says: current_midi_port=(dbc+j)%8;
1698                 => if we start at (dbc+stream->location-1)%8 [due to location_min=1],
1699                 we'll start at the right event for the midi port.
1700                 => if we increment j with 8, we stay at the right event.
1701                 */
1702                 // FIXME: as we know in advance how big a packet is (syt_interval) we can
1703                 //        predict how much loops will be present here
1704                 for(j = (dbc & 0x07)+mp->getLocation()-1; j < nevents; j += 8) {
1705                         target_event=(quadlet_t *)(data + ((j * m_dimension) + mp->getPosition()));
1706                         quadlet_t sample_int=ntohl(*target_event);
1707                         // FIXME: this assumes that 2X and 3X speed isn't used,
1708                         // because only the 1X slot is put into the ringbuffer
1709                         if(IEC61883_AM824_GET_LABEL(sample_int) != IEC61883_AM824_LABEL_MIDI_NO_DATA) {
1710                                 sample_int=(sample_int >> 16) & 0x000000FF;
1711                                 if(!mp->writeEvent(&sample_int)) {
1712                                         debugWarning("Packet port events lost\n");
1713                                         ok=false;
1714                                 }
1715                         }
1716                 }
1717
1718         }
1719        
1720         return ok;
1721 }
1722
1723 int AmdtpReceiveStreamProcessor::decodeMBLAEventsToPort(AmdtpAudioPort *p, quadlet_t *data,
1724                                            unsigned int offset, unsigned int nevents)
1725 {
1726         unsigned int j=0;
1727
1728 //      printf("****************\n");
1729 //      hexDumpQuadlets(data,m_dimension*4);
1730 //      printf("****************\n");
1731
1732         quadlet_t *target_event;
1733
1734         target_event=(quadlet_t *)(data + p->getPosition());
1735
1736         switch(p->getDataType()) {
1737                 default:
1738                 case Port::E_Int24:
1739                         {
1740                                 quadlet_t *buffer=(quadlet_t *)(p->getBufferAddress());
1741
1742                                 assert(nevents + offset <= p->getBufferSize());
1743
1744                                 buffer+=offset;
1745
1746                                 for(j = 0; j < nevents; j += 1) { // decode max nsamples
1747                                         *(buffer)=(ntohl((*target_event) ) & 0x00FFFFFF);
1748                                         buffer++;
1749                                         target_event+=m_dimension;
1750                                 }
1751                         }
1752                         break;
1753                 case Port::E_Float:
1754                         {
1755                                 const float multiplier = 1.0f / (float)(0x7FFFFF);
1756                                 float *buffer=(float *)(p->getBufferAddress());
1757
1758                                 assert(nevents + offset <= p->getBufferSize());
1759
1760                                 buffer+=offset;
1761
1762                                 for(j = 0; j < nevents; j += 1) { // decode max nsamples               
1763        
1764                                         unsigned int v = ntohl(*target_event) & 0x00FFFFFF;
1765                                         // sign-extend highest bit of 24-bit int
1766                                         int tmp = (int)(v << 8) / 256;
1767                
1768                                         *buffer = tmp * multiplier;
1769                                
1770                                         buffer++;
1771                                         target_event+=m_dimension;
1772                                 }
1773                         }
1774                         break;
1775         }
1776
1777         return 0;
1778 }
1779
1780 } // end of namespace FreebobStreaming
Note: See TracBrowser for help on using the browser.