MHEG5  18.9.0
MHEG5 Documentation
mh5stream.c
Go to the documentation of this file.
1 /*******************************************************************************
2  * Copyright © 2014 The DTVKit Open Software Foundation Ltd (www.dtvkit.org)
3  * Copyright © 2004 Ocean Blue Software Ltd
4  * Copyright © 2000 Koninklijke Philips Electronics N.V
5  *
6  * This file is part of a DTVKit Software Component
7  * You are permitted to copy, modify or distribute this file subject to the terms
8  * of the DTVKit 1.0 Licence which can be found in licence.txt or at www.dtvkit.org
9  *
10  * THIS CODE AND INFORMATION ARE PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND,
11  * EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES
12  * OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE.
13  *
14  * If you or your organisation is not a member of DTVKit then you have access
15  * to this source code outside of the terms of the licence agreement
16  * and you are expected to delete this and any associated files immediately.
17  * Further information on DTVKit, membership and terms can be found at www.dtvkit.org
18  *******************************************************************************/
32 /*---includes for this file--------------------------------------------------*/
33 #include "mh5application.h"
34 #include "mh5scene.h"
35 #include "mh5stream.h"
36 #include "mh5object.h" /* for actions */
37 #include "mh5variable.h" /* for actions */
38 #include "mh5memory.h" /* for constructor/destructor */
39 #include "mh5display.h" /* for actions */
40 #include "mh5streamevent.h" /* for stream events */
41 #include "mh5final.h"
42 #include "mh5queue.h" /* Events */
43 #include "mh5audio.h" /* for events */
44 #include "mh5video.h"
45 #include "mh5rtgraphics.h"
46 #include "mh5debug.h"
47 #include "mh5misc.h"
48 #include "mh5profile.h"
49 
50 #include "glue_main.h"
51 #include "dvb_service.h"
52 
53 #ifdef INCLUDE_ICS
54 #include "mh5streamer.h"
55 #endif
56 
57 #ifdef MH5PRINTOUT
58 #include <string.h>
59 #endif
60 
61 /*---constant definitions for this file--------------------------------------*/
62 
63 
64 /*---local typedef structs for this file-------------------------------------*/
65 
66 /*---local (static) variable declarations for this file----------------------*/
67 
68 static S_DVB_LOCATOR currentService = {0, 0, 0};
69 static MHEG5Int audioComponentTag = -1;
70 static MHEG5Int videoComponentTag = -1;
71 #ifndef MHEG5PROFILE_UK1_06
72 static MHEG5Int rtgraphicsComponentTag = -1;
73 #endif
74 
75 /*---local function definitions----------------------------------------------*/
76 
77 /*---global function definitions---------------------------------------------*/
78 
79 
86 #ifdef MH5PRINTOUT
87 void MHEG5streamPrint(MHEG5Stream *stream, char *out)
88 {
89  MHEG5Ingredient **currMultiplex = stream->multiplex;
90 
91  MHEG5ingredientPrint(&stream->ingredient, out);
92 
93  /*exchanged attributes */
94  MHEG5indent(out);
95  MHEG_PRINT(out, ":Multiplex (");
96  MHEG5newLine(out);
97  MHEG5incIndent();
98  while (*currMultiplex)
99  {
100  switch ((*currMultiplex)->root.clazz)
101  {
102  case MHEG5AUDIO:
103  MHEG5audioPrint((MHEG5Audio *) (*currMultiplex), out);
104  break;
105  case MHEG5VIDEO:
106  MHEG5videoPrint((MHEG5Video *) (*currMultiplex), out);
107  break;
108  #ifndef MHEG5PROFILE_UK1_06
109  case MHEG5RTGRAPHICS:
110  MHEG5rtgraphicsPrint((MHEG5RTGraphics *) (*currMultiplex), out);
111  break;
112  #endif
113  default:
114  MHEG5incIndent();
115  MHEG5indent(out);
116  MHEG_PRINT(out, "{");
117  MHEG5newLine(out);
118  }
119  MHEG5decIndent();
120  MHEG5indent(out);
121  MHEG_PRINT(out, "}");
122  MHEG5newLine(out);
123  currMultiplex++;
124  }
125  MHEG5decIndent();
126  MHEG5indent(out);
127  MHEG_PRINT(out, ")");
128  MHEG5newLine(out);
129 
130  if (stream->storageMemory)
131  {
132  MHEG5indent(out);
133  MHEG_PRINT(out, ":Storage ");
134  MHEG_PRINT(out, "memory");
135  MHEG5newLine(out);
136  }
137  if (stream->looping != 1)
138  {
139  MHEG5indent(out);
140  MHEG_PRINT(out, ":Looping ");
141  MHEG5intPrint(stream->looping, out);
142  MHEG5newLine(out);
143  }
144 
145 /* internal attributes
146  MHEG5indent(out);
147  MHEG_PRINT(out,"//:Speed: ");
148  MHEG5intPrint(stream->speed[0],out);
149  MHEG5newLine(out);
150 
151  MHEG5indent(out);
152  MHEG_PRINT(out," ");
153  MHEG5intPrint(stream->speed[1],out);
154  MHEG5newLine(out);
155 
156  MHEG5indent(out);
157  MHEG_PRINT(out,"//:CounterPosition: ");
158  MHEG5intPrint(stream->counterPosition,out);
159  MHEG5newLine(out);
160 
161  MHEG5indent(out);
162  MHEG_PRINT(out,"//:CounterEndPosition: ");
163  MHEG5intPrint(stream->counterEndPosition,out);
164  MHEG5newLine(out);
165 
166  MHEG5indent(out);
167  MHEG_PRINT(out,"//:CounterMaxPosition: ");
168  MHEG5intPrint(stream->counterMaxPosition,out);
169  MHEG5newLine(out);
170  */
171 /* engine data
172  MHEG5indent(out);
173  MHEG_PRINT(out,"// LoopsCompleted ");
174  MHEG5intPrint((int)stream->streamState,out);
175  MHEG5newLine(out);
176  */
177 }
178 
179 #endif
180 
187 {
188  assert(stream);
189 
191 
192  stream->storageMemory = MHEG5FALSE;
193  stream->looping = 1;
194 }
195 
204 {
205  assert(stream);
206 
207  if (!stream->storageMemory)
208  {
209  MHEG5streamRemove(stream);
210  }
211 
213 }
214 
228 {
229  MHEG5Ingredient *item;
230  MHEG5Int index;
231 
232  assert(stream);
233 
234  /* 1. Apply the first three steps of the Preparation behaviour as defined
235  * in the Root class.
236  * Root Prepare:
237  * 1. If the AvailabilityStatus attribute of the object is True, abort
238  * the behaviour.
239  */
240  assert(!stream->ingredient.root.runningStatus);
241  /* Root Prepare:
242  * Otherwise:
243  * 2. Retrieve the object from an entity outside the engine.
244  * - note - entity already retreived.
245  */
246 
247  /* Root Prepare:
248  * 3. Set each internal attribute of the object to its initial value.
249  */
252  {
253  /* Copy content reference */
255  stream->ingredient.content.ref.referenced.priority = stream->ingredient.originalContent.ref.referenced.priority;
256  }
257  else
258  {
259  /* Copy the included content */
261  }
262  stream->speed[0] = 1;
263  stream->speed[1] = 1;
264  stream->counterPosition = 0;
265  stream->counterEndPosition = -1;
266  stream->counterMaxPosition = -1;
267 
268  if (!stream->storageMemory)
269  {
270  MHEG5streamAdd(stream);
271  }
272 
273  assert(stream->counterTriggers == 0);
274 
275  /* 2. Apply the Activation behaviour to all StreamComponents of the Stream
276  * that have the InitiallyActive attribute set to True, in the order
277  * they appear in the Stream Multiplex.
278  */
279  for (index = 0; index < MAX_MLTPLX; index++)
280  {
281  item = stream->multiplex[index];
282  if (item == NULL)
283  {
284  break;
285  }
286 
287  if (!item->initiallyStopped)
288  {
289  switch (item->root.clazz)
290  {
291  case MHEG5VIDEO:
292  MHEG5videoActivate((MHEG5Video *) item);
293  break;
294  case MHEG5AUDIO:
295  MHEG5audioActivate((MHEG5Audio *) item);
296  break;
297  #ifndef MHEG5PROFILE_UK1_06
298  case MHEG5RTGRAPHICS:
299  #endif
300  default:;
301  }
302  }
303  }
304 
305  /* 3. Apply steps four to six of the Preparation behaviour as defined in
306  * the Root class.
307  */
308 
309  /* Root Prepare:
310  * 4. Set the AvailabilityStatus attribute to True.
311  */
313 
314  /* Root Prepare:
315  * 5. Generate an IsAvailable event.
316  */
318 
319  /* Root Prepare:
320  * 6. Perform the ContentPreparation behaviour.
321  */
322  TRACE(TSTRM, (" sp id=%ld", stream->ingredient.root.id))
324 }
325 
341 {
342  MHEG5Bool validContentHook;
343  assert(stream);
344 
345  if (!stream->ingredient.root.runningStatus)
346  {
347  TRACE(TSTRM, (" sa id=%ld name=%s", stream->ingredient.root.id, stream->ingredient.content.ref.referenced.reference.data))
348  if (!stream->ingredient.root.availabilityStatus)
349  {
350  MHEG5streamPrepare( stream );
351  }
352  /* Could call the base class activation behaviour, but *
353  MHEG5ingredientActivate(&stream->ingredient); <- does nothing, so don't bother */
354 
355  validContentHook = MHEG5FALSE;
356 
357  if (stream->storageMemory)
358  {
360  {
361  validContentHook = MHEG5TRUE;
362  }
363  }
364  else
365  {
366  if (stream->ingredient.contentHook == CHOOK_STREAM_NORMAL ||
368  {
369  validContentHook = MHEG5TRUE;
370  }
371  }
372 
373  if (validContentHook)
374  {
376  {
377  /* Stream events are only relevant to broadcast streams */
378  MHEG5notifyStreamRunning(stream);
379  }
380 
381  /* Play all stream items in the multiplex */
382  MHEG5displayStreamPlay(stream);
383  }
384  else
385  {
386  MHEG5displayStreamStop(stream);
387  }
388 
390  MHEG5sendSync((MHEG5Root *) stream, MHEG5ISRUNNING, 0);
391 
393  }
394 }
395 
407 {
408  MHEG5Bool update = MHEG5FALSE;
409 
410  assert(stream);
411 
412  if (stream->ingredient.root.runningStatus)
413  {
414  if (stream->ingredient.contentHook == CHOOK_STREAM_IC)
415  {
416  #ifdef INCLUDE_ICS
417  MHEG5StreamerStop(stream);
418  #endif
419 
420  MHEG5displayStreamStop(stream);
421  }
422  else
423  {
424  assert( MHEG5getCurrentApplication());
425  if (MHEG5getCurrentApplication()->streamContinuanceFlag == MHEG5FALSE)
426  {
427  MHEG5displayStreamStop(stream);
428  update = MHEG5TRUE;
429  }
430  }
431 
432  MHEG5notifyStreamStopped(stream);
434 
435  if (update)
436  {
438  }
439  }
440 }
441 
452 {
453  MHEG5CounterTrigger *ct2;
454 
455  assert(stream);
456 
458 
459  while (stream->counterTriggers)
460  {
461  ct2 = stream->counterTriggers;
462  stream->counterTriggers = stream->counterTriggers->next;
463  MHEG5freeMem(ct2);
464  }
465 
466  #ifdef INCLUDE_ICS
467  if (stream->ingredient.contentHook == CHOOK_STREAM_IC)
468  {
469  MHEG5StreamerRemove(stream);
470  }
471  #endif
472 }
473 
501 {
502  MHEG5Stream *stream;
503  MHEG5GList *thirdParam = 0;
504  MHEG5Int ti = 0, value = 0;
505  MHEG5CounterTrigger *ct, *ct2;
506 
507  assert(target);
508 
509  if (target->clazz != MHEG5STREAM)
510  {
511  return MHEG5ERR_WRONGTARGET;
512  }
513  if (!params)
514  {
516  }
517  stream = (MHEG5Stream *)target;
518  thirdParam = MHEG5resolveGenericInteger(params, &ti);
519  if (thirdParam)
520  {
521  MHEG5resolveGenericInteger(thirdParam, &value);
522  #ifdef INCLUDE_ICS
523  if (stream->ingredient.contentHook == CHOOK_STREAM_IC && value >= 0)
524  {
525  MHEG5StreamerSetCounterTrigger(stream, ti, value);
526  }
527  #endif
528  ct = stream->counterTriggers;
529  while (ct)
530  {
531  if (ct->id == ti)
532  {
533  ct->pos = value;
534  return MHEG5ERR_NOERROR;
535  }
536  ct = ct->next;
537  }
538  ct = MHEG5getMem(sizeof(MHEG5CounterTrigger));
539  if (ct == 0)
540  {
541  /* Out of memory - Silently ignore action */
542  return MHEG5ERR_NOERROR;
543  }
544  ct->id = ti;
545  ct->pos = value;
546  ct->next = stream->counterTriggers;
547  stream->counterTriggers = ct;
548  }
549  else
550  {
551  #ifdef INCLUDE_ICS
552  if (stream->ingredient.contentHook == CHOOK_STREAM_IC)
553  {
554  MHEG5StreamerSetCounterTrigger(stream, ti, -1);
555  }
556  #endif
557  ct = stream->counterTriggers;
558  ct2 = 0;
559  while (ct)
560  {
561  if (ct->id == ti)
562  {
563  if (ct2)
564  {
565  ct2->next = ct->next;
566  }
567  else
568  {
569  stream->counterTriggers = stream->counterTriggers->next;
570  }
571  MHEG5freeMem(ct);
572  return MHEG5ERR_NOERROR;
573  }
574  ct2 = ct;
575  ct = ct->next;
576  }
577  }
578  return MHEG5ERR_NOERROR;
579 }
580 
611 {
612  MHEG5GList *thirdParam = 0;
613  MHEG5Int s1 = 0; /* Numerator */
614  MHEG5Int s2 = 1; /* Denominator */
615  MHEG5Stream *s;
616 
617  /* Resolve target */
618  assert(target);
619 
620  if (target->clazz != MHEG5STREAM)
621  {
622  return MHEG5ERR_WRONGTARGET;
623  }
624 
625  /* Resolve numerator */
626  if (!params)
627  {
629  }
630  thirdParam = MHEG5resolveGenericInteger(params, &s1);
631 
632  /* Resolve optional denominator */
633  if (thirdParam)
634  {
635  MHEG5resolveGenericInteger(thirdParam, &s2);
636  }
637 
638 #ifndef MHEG5_STREAM_TRICK_MODES
639  /* If we do not support trick modes then set speed to be either 1/1 or 0/1
640  * for play or freeze respectivly.
641  */
642  if (((s1 > 0) && (s2 < 0)) || ((s1 < 0) && (s2 > 0)))
643  {
644  /* Result is negative - set numerator to 0 to freeze */
645  s1 = 0;
646  }
647  else if (s1 != 0)
648  {
649  /* Positive - set numerator to 1 for normal speed play */
650  s1 = 1;
651  }
652 
653  /* Always set denominator to 1 when trick modes are not supported */
654  s2 = 1;
655 #endif
656 
657  s = (MHEG5Stream *) target;
658  if (s1 != s->speed[0] || s2 != s->speed[1])
659  {
660  s->speed[0] = s1;
661  s->speed[1] = s2;
662 
663  if (target->runningStatus)
664  {
665  #ifdef INCLUDE_ICS
667  {
668  if (s1 == 0)
669  {
671  }
672  else
673  {
675  }
676  }
677  else
678  {
680  }
681  #else
683  #endif
684  }
685  }
686 
687  return MHEG5ERR_NOERROR;
688 }
689 
714 {
715  /* This action only has an effect on engines supporting stream trick
716  * modes.
717  */
718  MHEG5Int cp = 0;
719  MHEG5Stream *stream;
720 
721  if (target->clazz != MHEG5STREAM)
722  {
723  return MHEG5ERR_WRONGTARGET;
724  }
725  if (!params)
726  {
728  }
729 
730  stream = (MHEG5Stream *)target;
731 
732  MHEG5resolveGenericInteger(params, &cp);
733  stream->counterPosition = cp;
734  #ifdef INCLUDE_ICS
735  if (stream->ingredient.contentHook == CHOOK_STREAM_IC)
736  {
738  if (target->availabilityStatus && !target->runningStatus)
739  {
740  /* Set counter position on available / non-running
741  * stream = prepare (according to buffering model).
742  */
743  MHEG5StreamerPrepare(stream);
744  }
745  }
746  #endif
747 
748  return MHEG5ERR_NOERROR;
749 }
750 
786 {
787  MHEG5Stream *stream;
788  MHEG5Int cp = 0;
789 
790  if (target->clazz != MHEG5STREAM)
791  {
792  return MHEG5ERR_WRONGTARGET;
793  }
794 
795  if (!params)
796  {
798  }
799  MHEG5resolveGenericInteger(params, &cp);
800 
801  stream = (MHEG5Stream *)target;
802 
803  /* 2. Set the value of the CounterEndPosition attribute of the target
804  * Stream to NewCounterEndPosition.
805  */
806  stream->counterEndPosition = cp;
807 
808  /* 3. If the target Stream is active and NewCounterEndPosition is already
809  * passed, stop the target Stream. If Looping is not equal to 1, a new
810  * looping play back shall be played. (from COR.1)
811  */
812  if (stream->ingredient.contentHook == CHOOK_STREAM_IC)
813  {
814  #ifdef INCLUDE_ICS
816  #endif
817  }
818  else
819  {
820  if ((target->runningStatus) && (cp < stream->counterPosition))
821  {
822  MHEG5displayStreamStop(stream);
823  if (stream->looping != 1)
824  {
825  MHEG5displayStreamPlay(stream);
826  }
827  }
828  }
829 
830  return MHEG5ERR_NOERROR;
831 }
832 
850 {
851  MHEG5ErrorCode error_val;
852  MHEG5Root *cpVar;
853 
854  if (target->clazz != MHEG5STREAM)
855  {
856  return MHEG5ERR_WRONGTARGET;
857  }
858 
859  if (!params)
860  {
862  }
863 
864  MHEG5resolveORef(params, &cpVar);
865  if (!cpVar)
866  {
867  error_val = MHEG5ERR_WRONGNUMBEROFPARAMS;
868  }
869  else if (!cpVar->runningStatus)
870  {
871  error_val = MHEG5ERR_PARAMNOTACTIVE;
872  }
873  else if (cpVar->clazz == MHEG5INTEGERVARIABLE)
874  {
875  MHEG5Stream *s = (MHEG5Stream *)target;
876  #ifdef INCLUDE_ICS
878  {
880  }
881  #endif /* INCLUDE_ICS */
882  ((MHEG5IntegerVariable *) cpVar)->value = s->counterPosition;
883  error_val = MHEG5ERR_NOERROR;
884  }
885  else
886  {
887  error_val = MHEG5ERR_WRONGPARAM;
888  }
889 
890  return error_val;
891 }
892 
910 {
911  MHEG5ErrorCode error_val;
912  MHEG5Root *cmpVar;
913 
914  if (!target)
915  {
917  }
918 
919  if (target->clazz != MHEG5STREAM)
920  {
921  return MHEG5ERR_WRONGTARGET;
922  }
923 
924  if (!params)
925  {
927  }
928 
929  MHEG5resolveORef(params, &cmpVar);
930  if (!cmpVar->runningStatus)
931  {
932  error_val = MHEG5ERR_PARAMNOTACTIVE;
933  }
934  else if (cmpVar->clazz == MHEG5INTEGERVARIABLE)
935  {
936  MHEG5Stream *s = (MHEG5Stream *)target;
937  #ifdef INCLUDE_ICS
939  {
941  }
942  #endif /* INCLUDE_ICS */
943  ((MHEG5IntegerVariable *) cmpVar)->value = s->counterMaxPosition;
944  error_val = MHEG5ERR_NOERROR;
945  }
946  else
947  {
948  error_val = MHEG5ERR_WRONGPARAM;
949  }
950 
951  return error_val;
952 }
953 
960 {
961  if (stream->dvbLocator.service_id != 0)
962  {
963  S_DVB_LOCATOR defaultLocator;
964  MHEG5GetDefaultService(&defaultLocator);
965  if (stream->dvbLocator.service_id != defaultLocator.service_id)
966  {
968  }
969  }
970  /* Clear the multiplex reference for stream objects. */
971  memset(&stream->dvbLocator, 0, sizeof(S_DVB_LOCATOR));
972 }
973 
982 {
983  /* Check the content hook */
984  TRACE(TSTRM, (" strm cntnt %d", stream->ingredient.root.runningStatus))
986  {
987  /* Content hook indicates a memory format. We expect the Storage
988  * exchanged attribute to indicate storage type memory.
989  */
990  if (stream->storageMemory)
991  {
992  /* This is an MPEG2 audio file */
993  TRACE(TSTRM, (" cRef=%d", stream->ingredient.content.referenced))
994  if (stream->ingredient.content.referenced)
995  {
996  /* Make a copy of the referenced content */
997  stream->ingredient.data = MHEG5getMem(content->size);
998  if (stream->ingredient.data)
999  {
1000  memcpy(stream->ingredient.data, content->data, content->size );
1001  stream->ingredient.dataLen = content->size;
1002  }
1003  else
1004  {
1005  ERROR_PRINT(("ERROR: failed to get memory\n"));
1006  }
1007  }
1008  else
1009  {
1010  ERROR_PRINT(("ERROR: Illegal included content for stream from memory\n"));
1011  }
1012  }
1013  else
1014  {
1015  ERROR_PRINT(("ERROR: Illegal combination of cHook %ld and storage stream\n", stream->ingredient.contentHook));
1016  }
1017  }
1018  else if (stream->ingredient.contentHook == CHOOK_STREAM_NORMAL)
1019  {
1020  /* Content hook indicates a stream format. We expect the Storage
1021  * exchanged attribute to indicate storage type stream.
1022  */
1023  if (!stream->storageMemory)
1024  {
1025  S_DVB_LOCATOR defaultLocator;
1026 
1027  MHEG5GetDefaultService(&defaultLocator);
1028  if (stream->dvbLocator.service_id != 0 &&
1029  stream->dvbLocator.service_id != defaultLocator.service_id)
1030  {
1032  }
1033 
1034  if (content->size == sizeof(S_DVB_LOCATOR))
1035  { /* This is a dsmcc stream object or DVB URL */
1036  /* retrieve dvb locator from 'data' field */
1037  stream->dvbLocator = *((S_DVB_LOCATOR *)content->data);
1038 
1039  if (stream->dvbLocator.service_id != 0 &&
1040  stream->dvbLocator.service_id != defaultLocator.service_id)
1041  {
1043  }
1044 
1045  if (stream->dsmClearFunc)
1046  {
1047  assert( stream->dsmRef != NULL );
1048  stream->dsmClearFunc(stream->dsmRef);
1049  }
1050  else
1051  {
1052  assert( stream->dsmRef == NULL );
1053  }
1054 
1055  if (content->destroy != NULL)
1056  {
1057  /* retrieve DSM-CC clear function stuff */
1058  stream->dsmClearFunc = content->destroy;
1059  stream->dsmRef = content->fs_handle;
1060  content->destroy = NULL;
1061  content->fs_handle = NULL;
1062  }
1063  else
1064  {
1065  stream->dsmClearFunc = NULL;
1066  stream->dsmRef = NULL;
1067  }
1068  }
1069  else
1070  {
1071  ERROR_PRINT(("ERROR: Illegal content length %d for storage stream\n", content->size));
1072  stream->dvbLocator = defaultLocator;
1073  }
1074  }
1075  else
1076  {
1077  ERROR_PRINT(("ERROR: Illegal combination of cHook %ld and storage stream\n", stream->ingredient.contentHook));
1078  }
1079  }
1080  else if (stream->ingredient.contentHook == CHOOK_STREAM_IC)
1081  {
1082  /* Nothing to do */
1083  }
1084  else
1085  {
1086  ERROR_PRINT(("ERROR: invalid chook for Stream %ld\n", stream->ingredient.contentHook));
1087  }
1088 }
1089 
1099 {
1100  TRACE(TSTRM, ("netw_id=0x%x srv_id=0x%x (%d)", currentService.original_network_id, currentService.service_id, currentService.service_id))
1101  /* Already caching the current service */
1102  if (currentService.original_network_id != 0)
1103  {
1104  *multiplexRef = currentService;
1105  return MHEG5TRUE;
1106  }
1107 
1108  /* Try to find the current service */
1110  if (currentService.original_network_id != 0)
1111  {
1112  *multiplexRef = currentService;
1113  return MHEG5TRUE;
1114  }
1115 
1116  /* Unable to find a running Stream multiplex object -
1117  * set multiplex ref to default service.
1118  */
1119  MHEG5GetDefaultService(multiplexRef);
1120  return MHEG5FALSE;
1121 }
1122 
1130 {
1131  MHEG5Group *group;
1132  MHEG5Bool found = MHEG5FALSE;
1133  int i;
1134 
1135  if (currentService.original_network_id != 0)
1136  {
1137  /* Current service already known */
1138  return;
1139  }
1140 
1141  /* Search application first */
1143  for (i = 0; i < 2; i++)
1144  {
1145  MHEG5Ingredient *item = 0;
1146 
1147  /* The first time we enter this loop, group is set to the current
1148  * application. The second time round it is set to the current scene.
1149  */
1150  if (group)
1151  {
1152  item = group->itemHead;
1153  }
1154 
1155  /* Search all items in this group looking for stream objects */
1156  while (item != 0)
1157  {
1158  if ((item->root.clazz == MHEG5STREAM) &&
1159  (((MHEG5Stream *)item)->dvbLocator.original_network_id != 0))
1160  {
1161  MHEG5Ingredient *multiplexItem;
1162  MHEG5Int index;
1163 
1164  /* Search all multiplex items */
1165  for (index = 0; index < MAX_MLTPLX; index++)
1166  {
1167  multiplexItem = ((MHEG5Stream *)item)->multiplex[index];
1168  if (multiplexItem == NULL)
1169  {
1170  break;
1171  }
1172 
1173  if (multiplexItem->root.runningStatus)
1174  {
1175  switch (multiplexItem->root.clazz)
1176  {
1177  case MHEG5VIDEO:
1178  /* Found a video object. These have priority, so
1179  * the search is over.
1180  */
1181  currentService = ((MHEG5Stream *)item)->dvbLocator;
1182  TRACE(TSTRM, ("STM=%p netw_id=0x%x srv_id=0x%x (%d)", item, currentService.original_network_id,
1183  currentService.service_id, currentService.service_id))
1184  return;
1185  case MHEG5AUDIO:
1186  /* Found an audio object. Remember the
1187  * reference and the fact that we've found
1188  * an audio object to avoid overwriting
1189  * with RTGraphics reference
1190  */
1191  currentService = ((MHEG5Stream *)item)->dvbLocator;
1192  found = MHEG5TRUE;
1193  break;
1194  #ifndef MHEG5PROFILE_UK1_06
1195  case MHEG5RTGRAPHICS:
1196  if (!found)
1197  {
1198  /* This is an RTGraphics object. Only
1199  * remember the reference if we have not
1200  * already found either an Audio or
1201  * RTGraphics object.
1202  */
1203  currentService = ((MHEG5Stream *)item)->streamRef.multiplex;
1204  found = MHEG5TRUE;
1205  }
1206  #endif
1207  default:;
1208  }
1209  }
1210  }
1211  }
1212  item = item->next;
1213  }
1214  /* Repeat the loop searching the scene objects */
1215  group = (MHEG5Group *)MHEG5getCurrentScene();
1216  }
1217  if (!found)
1218  {
1219  currentService.original_network_id = 0;
1220  currentService.transport_stream_id = 0;
1221  currentService.service_id = 0;
1222  }
1223  TRACE(TSTRM, ("netw_id=0x%x srv_id=0x%x (%d)", currentService.original_network_id,
1224  currentService.service_id, currentService.service_id))
1225 }
1226 
1234  S_DvbComponent *service)
1235 {
1236  if (item != 0 && service != 0)
1237  {
1238  if (service->original_network_id != 0)
1239  {
1240  currentService.original_network_id = service->original_network_id;
1241  }
1242  if (service->transport_stream_id != 0)
1243  {
1244  currentService.transport_stream_id = service->transport_stream_id;
1245  }
1246  if (service->service_id != 0)
1247  {
1248  currentService.service_id = service->service_id;
1249  }
1250  switch (((MHEG5Root *)item)->clazz)
1251  {
1252  case MHEG5AUDIO:
1253  audioComponentTag = service->ComponentTag;
1254  break;
1255  case MHEG5VIDEO:
1256  videoComponentTag = service->ComponentTag;
1257  break;
1258  #ifndef MHEG5PROFILE_UK1_06
1259  case MHEG5RTGRAPHICS:
1260  rtgraphicsComponentTag = service->componentTag;
1261  break;
1262  #endif
1263  default:
1264  ERROR_PRINT(("ERROR: MHEG5streamSetCurrentService: Invalid object class in stream object multiplex\n"));
1265  }
1266  TRACE(TSTRM, ("srv_id=0x%x AC=%d VC=%d", currentService.service_id, audioComponentTag, videoComponentTag))
1267  }
1268 }
1269 
1275 {
1276  TRACE(TSTRM, ("srv_id=0x%x AC=%d VC=%d", currentService.service_id, audioComponentTag, videoComponentTag))
1277  currentService.original_network_id = 0;
1278  currentService.transport_stream_id = 0;
1279  currentService.service_id = 0;
1280  audioComponentTag = -1;
1281  videoComponentTag = -1;
1282  #ifndef MHEG5PROFILE_UK1_06
1283  rtgraphicsComponentTag = -1;
1284  #endif
1285 }
1286 
1294 {
1295  MHEG5Stream *stream = 0;
1296  MHEG5Int componentTag = -1;
1297  MHEG5Int currentComponentTag = -1;
1298  MHEG5Int result = -1;
1299 
1300  switch (item->root.clazz)
1301  {
1302  case MHEG5AUDIO:
1303  stream = ((MHEG5Audio *)item)->parent;
1304  componentTag = ((MHEG5Audio *)item)->componentTag;
1305  currentComponentTag = audioComponentTag;
1306  break;
1307  case MHEG5VIDEO:
1308  stream = ((MHEG5Video *)item)->parent;
1309  componentTag = ((MHEG5Video *)item)->componentTag;
1310  currentComponentTag = videoComponentTag;
1311  break;
1312  #ifndef MHEG5PROFILE_UK1_06
1313  case MHEG5RTGRAPHICS:
1314  stream = ((MHEG5RTGraphics *)item)->parent;
1315  componentTag = ((MHEG5RTGraphics *)item)->componentTag;
1316  currentComponentTag = rtgraphicsComponentTag;
1317  break;
1318  #endif
1319  default:
1320  ERROR_PRINT(("ERROR: MHEG5streamGetComponentTag: ingredient is not a multiplex component\n"));
1321  }
1322 
1323  if (stream != 0)
1324  {
1325  /* Valid multiplex component */
1326  MHEG5String *ref = &stream->ingredient.content.ref.referenced.reference;
1327  if (strncmp((char *)ref->data, "rec://svc/cur", ref->len) == 0)
1328  {
1329  TRACE(TSTRM, ("srv_id=0x%x AC=%d VC=%d", currentService.service_id, audioComponentTag, videoComponentTag))
1330  if (componentTag == -1)
1331  {
1332  result = currentComponentTag;
1333  }
1334  else
1335  {
1336  result = -1;
1337  }
1338  }
1339  else
1340  {
1341  result = componentTag;
1342  }
1343  TRACE(TSTRM, ("CT=%d", result))
1344  }
1345 
1346  return result;
1347 }
1348 
MHEG5Bool availabilityStatus
Definition: mh5root.h:52
void MHEG5StreamerResume(MHEG5Stream *stream)
Resume IP content streaming after it was paused by MHEG5StreamerPause.
void MHEG5ingredientInit(MHEG5Ingredient *ingredient)
Initialise a ingredient object with default values.
MHEG5Byte * data
Definition: mh5ingredient.h:80
MHEG5ErrorCode MHEG5getCounterPosition(MHEG5Root *target, MHEG5GList *params)
Implementation of the GetCounterPosition (Target, CounterPositionVar) action of the stream class...
Definition: mh5stream.c:849
MHEG5Int counterMaxPosition
Definition: mh5stream.h:78
MHEG5ErrorCode MHEG5setSpeed(MHEG5Root *target, MHEG5GList *params)
The effect of this action is to change the speed in which the stream is displayed. Implementation of the SetSpeed (Target, NewSpeed) action of the stream class. SetSpeed (NewSpeed) Change the presentation speed of a stream. Execute the following sequence of actions:
Definition: mh5stream.c:610
MHEG5CounterTrigger * counterTriggers
Definition: mh5stream.h:77
Distributor for Prepare, Destruct, Activate, Deactivate and Clone calls. Distribute the +Prepare +Des...
F_DESTROY destroy
Definition: fs_types.h:56
void MHEG5StreamerSetCounterPosition(MHEG5Stream *stream)
Set the counter position of a stream in the streamer. This function uses the counter position as set ...
#define MAX_MLTPLX
Definition: mh5stream.h:41
U32BIT size
Definition: fs_types.h:54
MHEG5Ingredient ingredient
Definition: mh5stream.h:65
MHEG5Int MHEG5streamGetComponentTag(MHEG5Ingredient *item)
Get component tag for ingredient. This depends on the stream&#39;s content and the component tag of the i...
Definition: mh5stream.c:1293
Implementation of the RTGraphics class Description Defines the attributes and behaviour of non-persis...
MHEG5Int id
Definition: mh5stream.h:56
void MHEG5StreamerPrepare(MHEG5Stream *stream)
Prepare for retrieval of a stream from the IP connection.
U16BIT original_network_id
Definition: dvblocator.h:39
void MHEG5streamRemove(MHEG5Stream *stream)
Remove an MHEG-5 Stream Object from repository.
S_DVB_LOCATOR dvbLocator
Definition: mh5stream.h:82
void MHEG5StreamerSetCounterEndPosition(MHEG5Stream *stream)
Set the counter end position of a stream in the streamer. This function uses the counter end position...
U16BIT transport_stream_id
Definition: dvblocator.h:40
MHEG5Int pos
Definition: mh5stream.h:57
Implementation of the Video class Description Defines the attributes and behaviour of an elementary v...
void MHEG5displayUpdate(void)
Update the display, redrawing any visible objects that are in the dirty rectangle.
Definition: mh5display.c:2035
#define CHOOK_STREAM_NORMAL
Definition: mh5profile.h:107
void MHEG5notifyStreamStopped(MHEG5Stream *stream)
Notify that a stream has stopped.
MHEG5GList * MHEG5resolveGenericInteger(MHEG5GList *params, MHEG5Int *value)
Definition: mh5object.c:510
Implement the MHEG5 Stream Class Stream Class Defines the behaviour of a composition of continuous me...
MHEG5Int looping
Definition: mh5stream.h:71
void MHEG5streamAdd(MHEG5Stream *stream)
Add an MHEG-5 Stream Object to repository.
MHEG5ErrorCode MHEG5setCounterPosition(MHEG5Root *target, MHEG5GList *params)
The effect of this action is to set the display counter to a new position. Implementation of the SetC...
Definition: mh5stream.c:713
#define MHEG5getMem
Definition: glue_memory.h:93
MHEG5Final clazz
Definition: mh5root.h:55
void MHEG5ingredientDestruct(MHEG5Ingredient *ingredient)
Implementation of the Destruction behaviour Execute the following sequence of actions: ...
Stream event subscription management.
Miscellaneous.
MHEG5ContentBody content
Definition: mh5ingredient.h:75
MHEG5Int counterEndPosition
Definition: mh5stream.h:76
void MHEG5GetDefaultService(S_DVB_LOCATOR *dvb_locator)
Definition: glue_main.c:1186
U16BIT transport_stream_id
Definition: dvblocator.h:33
MHEG5String MHEG5stringCopy(MHEG5String source)
<Function description>="">
Definition: mh5base.c:574
void MHEG5ingredientContentPrepare(MHEG5Ingredient *ingredient)
Implementation of the ContentPrepare behaviour COR.1 6.6: ContentPreparation Apply the following sequ...
Implement the MHEG5 Variable Class 21 Variable Class Defines a variable within the context of a Group...
void DVB_MhegServiceRemovePmtListen(S_DvbLocator dvbLocator)
Advise DVB stack to remove prioritising of PMT for the service that was set up by DVB_MhegServiceAddP...
void MHEG5streamFree(MHEG5Stream *stream)
Free off all memory associated with the specified object, including any exchanged attributes and inte...
Definition: mh5stream.c:203
U16BIT original_network_id
Definition: dvblocator.h:32
S32BIT MHEG5StreamerGetCounterPosition(MHEG5Stream *stream)
Return the current counter position (in units of 188 bytes).
long MHEG5Int
Definition: mh5base.h:73
MHEG5Int speed[2]
Definition: mh5stream.h:74
MHEG5ErrorCode MHEG5getCounterMaxPosition(MHEG5Root *target, MHEG5GList *params)
Implementation of the GetCounterMaxPosition (Target, CounterPositionVar) action of the stream class...
Definition: mh5stream.c:909
void MHEG5videoActivate(MHEG5Video *video)
Apply the activation behaviour of the video class.
Definition: mh5video.c:141
void MHEG5notifyStreamRunning(MHEG5Stream *stream)
Notify that a stream is running.
DVB Service information functions are required by MHEG5 engine. All required functions should be non-...
#define MHEG5freeMem
Definition: glue_memory.h:94
F_DESTROY dsmClearFunc
Definition: mh5stream.h:83
API for IC streamer.
This file defines the profile for the MHEG engine.
void MHEG5streamDestruct(MHEG5Stream *stream)
Destruct a stream object. Execute the following sequence of actions:
Definition: mh5stream.c:451
void DVB_MhegServiceAddPmtListen(S_DvbLocator dvbLocator)
Advise DVB stack that PMT may be required soon in DVB_MhegVideoPlayStream() or DVB_MhegAudioPlayStrea...
void MHEG5StreamerStop(MHEG5Stream *stream)
Stop streaming IP content.
short MHEG5Bool
Definition: mh5base.h:71
MHEG5ErrorCode
Definition: mh5base.h:222
MHEG5Bool storageMemory
Definition: mh5stream.h:69
Event handling. Implementation of a combined queue for events and actions. This is the eventsystem wh...
S32BIT MHEG5StreamerGetCounterMaxPosition(MHEG5Stream *stream)
Return the counter maximum position (content length in units of 188 bytes).
#define CHOOK_STREAM_MEMORY
Definition: mh5profile.h:108
void MHEG5streamInit(MHEG5Stream *stream)
Debug function.
Definition: mh5stream.c:186
MHEG5Byte * data
Definition: mh5base.h:85
void MHEG5displayStreamPlay(MHEG5Stream *stream)
Begin playback of all active components in the specifed stream object.
Definition: mh5display.c:2399
#define MHEG5TRUE
Definition: mh5base.h:49
MHEG5Bool initiallyStopped
Definition: mh5ingredient.h:71
void MHEG5ingredientDeactivate(MHEG5Ingredient *ingredient)
Implementation of Deactivate behaviour Inherrited from Root class.
Implement functions to retrieve MHEG5objects by GroupID and ID.
MHEG5Ingredient * multiplex[MAX_MLTPLX]
Definition: mh5stream.h:68
Implementation of the MHEG5 Application Class Defines a set of Ingredient objects, which are shared within an application scope. Base class: Group Subclasses: None Status: Concrete class.
Implementation of the MHEG5 Scene Class Scene Class Defines a set of Ingredient objects to be activat...
MHEG5Ingredient * itemHead
Definition: mh5group.h:62
Mheg5 logging and debug printing.
void MHEG5audioActivate(MHEG5Audio *audio)
Apply the activation behaviour off the audio class. Apply the activation behaviour of the base class...
Definition: mh5audio.c:144
U16BIT service_id
Definition: dvblocator.h:34
MHEG5Bool runningStatus
Definition: mh5root.h:51
MHEG5Int counterPosition
Definition: mh5stream.h:75
redirection include
MHEG5Int id
Definition: mh5root.h:48
void MHEG5streamActivate(MHEG5Stream *stream)
Apply the activation behaviour of the stream class. Execute the following sequence of actions: ...
Definition: mh5stream.c:340
U16BIT service_id
Definition: dvblocator.h:41
#define ERROR_PRINT(x)
Definition: mh5debug.h:76
MHEG5ErrorCode MHEG5setCounterEndPosition(MHEG5Root *target, MHEG5GList *params)
Implementation of the SetCounterEndPosition (Target, NewPosition) action of the stream class...
Definition: mh5stream.c:785
MHEG5Scene * MHEG5getCurrentScene(void)
<Function description>="">
Definition: mh5scene.c:207
FS_HANDLE dsmRef
Definition: mh5stream.h:84
S16BIT ComponentTag
Definition: dvblocator.h:42
union sMHEG5ContentBody::@2 ref
MHEG5Int len
Definition: mh5base.h:84
MHEG5Bool MHEG5streamGetCurrentService(S_DVB_LOCATOR *multiplexRef)
Return the current service (i.e. the service corresponding to the currently running Video...
Definition: mh5stream.c:1098
void MHEG5StreamerRemove(MHEG5Stream *stream)
Remove streaming IP request.
void MHEG5streamFindCurrentService(void)
Find the current service (i.e. the service corresponding to the currently running Video...
Definition: mh5stream.c:1129
void MHEG5streamDeactivate(MHEG5Stream *stream)
Apply the deactivation behaviour of the stream class. Execute the following sequence of actions: ...
Definition: mh5stream.c:406
MHEG5ContentBody originalContent
Definition: mh5ingredient.h:70
U8BIT * data
Definition: fs_types.h:55
void MHEG5streamContentAdapt(MHEG5Stream *stream, S_CONTENT *content)
Adapt new content for Stream objects. Content is either a DSM-CC stream object, a DVB URL or an MPEG2...
Definition: mh5stream.c:981
MHEG5ErrorCode MHEG5setCounterTrigger(MHEG5Root *target, MHEG5GList *params)
The effect of this action is to update the list of CounterTriggers for a Stream object SetCounterTrig...
Definition: mh5stream.c:500
MHEG5GList * MHEG5resolveORef(MHEG5GList *params, MHEG5Root **object)
Definition: mh5object.c:126
void MHEG5StreamerSetCounterTrigger(MHEG5Stream *stream, S32BIT triggerId, S32BIT newValue)
Add, remove or update a counter trigger for the stream. If the trigger does not exist, it will be added. If it already exists it will be updated if the new value is non-negative, otherwise it will be removed.
void MHEG5ingredientFree(MHEG5Ingredient *ingredient)
Free off all memory associated with the specified object, including any exchanged attributes and inte...
Implement the MHEG5 Audio Class Audio Class Defines the attributes and behaviour of an elementary aud...
void MHEG5streamContentClear(MHEG5Stream *stream)
Clear content for Stream objects.
Definition: mh5stream.c:959
MHEG5Bool referenced
Definition: mh5ingredient.h:49
Implement generic MHEG5-display functions - independent from the OSD These are generic functions used...
FS_HANDLE fs_handle
Definition: fs_types.h:57
void MHEG5StreamerPause(MHEG5Stream *stream)
Pause IP content streaming.
struct scounterTrigger * next
Definition: mh5stream.h:58
MHEG5Int contentHook
Definition: mh5ingredient.h:69
#define CHOOK_STREAM_IC
Definition: mh5profile.h:111
void MHEG5streamSetCurrentService(MHEG5Ingredient *item, S_DvbComponent *service)
Set the current service.
Definition: mh5stream.c:1233
void MHEG5displayStreamStop(MHEG5Stream *stream)
Stops playback of all active component of the specified stream object.
Definition: mh5display.c:2487
void MHEG5streamClearCurrentService(void)
Clear the current service.
Definition: mh5stream.c:1274
void MHEG5streamPrepare(MHEG5Stream *stream)
Apply the preparation behaviour of the stream class.
Definition: mh5stream.c:227
MHEG5String included
Definition: mh5ingredient.h:52
#define MHEG5FALSE
Definition: mh5base.h:48
void MHEG5sendSync(MHEG5Root *source, MHEG5EventType event, MHEG5Int data)
Store an event in the synchronous event queue.
Definition: mh5queue.c:1651
MHEG5Application * MHEG5getCurrentApplication(void)
<Function description>="">
#define TRACE(t, x)
Definition: glue_debug.h:118