MythTV  master
atscdescriptors.cpp
Go to the documentation of this file.
1 // -*- Mode: c++ -*-
2 // Copyright (c) 2003-2004, Daniel Thor Kristjansson
3 
4 #include <algorithm>
5 using namespace std;
6 
7 #include "atscdescriptors.h"
8 #include "mythlogging.h"
9 #include "iso639.h"
10 #include "atsc_huffman.h"
11 
12 using namespace std;
13 
14 
16 {
17  uint ct = CompressionType(i, j);
18  if (0 == ct)
19  return QString("no compression");
20  if (1 == ct)
21  return QString("Huffman Coding using C.4, C.5");
22  if (2 == ct)
23  return QString("Huffman Coding using C.6, C.7");
24  if (ct < 0xaf)
25  return QString("reserved");
26  return QString("compression not used by ATSC in North America, unknown");
27 }
28 
30 {
31  QString str;
32  if (1 == StringCount() && 1 == SegmentCount(0))
33  {
34  str.append(QString("lang(%1) ").arg(LanguageString(0)));
35  if (0 != Bytes(0, 0))
36  str.append(GetSegment(0, 0));
37  return str;
38  }
39 
40  str.append(QString("MultipleStringStructure count(%1)")
41  .arg(StringCount()));
42 
43  for (uint i = 0; i < StringCount(); i++)
44  {
45  str.append(QString(" String #%1 lang(%2:%3)")
46  .arg(i).arg(LanguageString(i))
47  .arg(LanguageKey(i)));
48 
49  if (SegmentCount(i) > 1)
50  str.append(QString(" segment count(%1)").arg(SegmentCount(i)));
51 
52  for (uint j=0; j<SegmentCount(i); j++)
53  str.append(QString(" Segment #%1 ct(%2) str(%3)").arg(j)
54  .arg(CompressionType(i, j)).arg(GetSegment(i, j)));
55  }
56 
57  return str;
58 }
59 
60 static uint maxPriority(const QMap<uint,uint> &langPrefs)
61 {
62  uint max_pri = 0;
63  for (uint pref : qAsConst(langPrefs))
64  max_pri = max(max_pri, pref);
65  return max_pri;
66 }
67 
69  QMap<uint,uint> &langPrefs) const
70 {
71  uint match_idx = 0;
72  uint match_pri = 0;
73 
74  for (uint i = 0; i < StringCount(); i++)
75  {
76  QMap<uint,uint>::const_iterator it =
77  langPrefs.find(CanonicalLanguageKey(i));
78  if ((it != langPrefs.end()) && (*it > match_pri))
79  {
80  match_idx = i;
81  match_pri = *it;
82  }
83  }
84 
85  if (match_pri)
86  return match_idx;
87 
88  if (StringCount())
89  langPrefs[CanonicalLanguageKey(0)] = maxPriority(langPrefs) + 1;
90 
91  return 0;
92 }
93 
94 QString MultipleStringStructure::GetBestMatch(QMap<uint,uint> &langPrefs) const
95 {
96  if (StringCount())
97  return GetFullString(GetIndexOfBestMatch(langPrefs));
98  return QString();
99 }
100 
102 {
103  const unsigned char* buf = (Offset(i, j)+3);
104  int len = Bytes(i, j);
105 
106  if (len <= 0)
107  return "";
108 
109  int ct = CompressionType(i, j);
110 
111  if (ct == 0)
112  return Uncompressed(buf, len, Mode(i, j));
113 
114  if (ct < 3)
115  return atsc_huffman1_to_string(buf, len, ct);
116 
117  return QString("MSS unknown text compression %1").arg(ct);
118 }
119 
121 {
122  QString tmp = "";
123  for (uint j = 0; j < SegmentCount(i); j++)
124  tmp += GetSegment(i, j);
125  return tmp.simplified();
126 }
127 
129  const unsigned char* buf, int len, int mode) {
130 
131  QString str=QString("");
132  if (mode<=6 ||
133  (9<=mode && mode<=0xe) ||
134  (0x10==mode) ||
135  (0x20<=mode && mode<=0x27) ||
136  (0x30<=mode && mode<=0x33)) { // basic runlength encoding
137  int hb=mode<<8;
138  for (int j=0; j<len; j++)
139  {
140 #if 0
141  LOG(VB_GENERAL, LOG_DEBUG, QString("str.append(0x%1:0x%2) -> %3")
142  .arg(mode, 0, 16) .arg(buf[j], 0, 16) .arg(QChar(hb|buf[j])));
143 #endif
144  if (hb|buf[j])
145  str.append( QChar( hb|buf[j] ) );
146  }
147  } else if (mode==0x3e) {
148  // Standard Compression Scheme for Unicode (SCSU)
149  str=QString("TODO SCSU encoding");
150  } else if (mode==0x3f) { // Unicode, UTF-16 Form
151  const auto* ustr = reinterpret_cast<const unsigned short*>(buf);
152  for (int j=0; j<(len>>1); j++)
153  str.append( QChar( (ustr[j]<<8) | (ustr[j]>>8) ) );
154  } else if (0x40<=mode && mode<=0x41)
155  str = QString("TODO Tawain Characters");
156  else if (0x48==mode)
157  str = QString("TODO South Korean Characters");
158  else
159  str = QString("unknown character encoding mode(%0)").arg(mode);
160  return str;
161 }
162 
164 {
165  m_ptrs.clear();
166  m_ptrs[Index(0,-1)] = m_data + 1;
167  for (uint i = 0; i < StringCount(); i++)
168  {
169  m_ptrs[Index(i,0)] = Offset(i,-1) + 4;
170  uint j = 0;
171  for (; j < SegmentCount(i); j++)
172  m_ptrs[Index(i,j+1)] = Offset(i,j) + Bytes(i,j) + 3;
173  m_ptrs[Index(i+1,-1)] = Offset(i,j);
174  }
175 }
176 
178 {
179  m_ptrs.clear();
180  m_ptrs[Index(0,-1)] = m_data+3;
181 
182  for (uint i = 0; i < ServicesCount(); i++)
183  m_ptrs[Index(i+1,-1)] = Offset(i,-1) + 6;
184 
185  return true;
186 }
187 
189 {
190  QString str("Caption Service Descriptor ");
191  str.append(QString("services(%2)").arg(ServicesCount()));
192 
193  for (uint i = 0; i < ServicesCount(); i++)
194  {
195  str.append(QString("\n lang(%1) type(%2) ")
196  .arg(LanguageString(i)).arg(static_cast<int>(Type(i))));
197  str.append(QString("easy_reader(%1) wide(%2) ")
198  .arg(static_cast<int>(EasyReader(i))).arg(static_cast<int>(WideAspectRatio(i))));
199  if (Type(i))
200  {
201  str.append(QString("service_num(%1)")
202  .arg(CaptionServiceNumber(i)));
203  }
204  else
205  {
206  str.append(QString("line_21_field(%1)").arg(static_cast<int>(Line21Field(i))));
207  }
208  }
209 
210  return str;
211 }
212 
214 {
215  m_ptrs.clear();
216  m_ptrs[Index(0,-1)] = m_data + 2;
217 
218  for (uint i = 0; i < RatingRegionCount(); i++)
219  {
220  m_ptrs[Index(i,0)] = Offset(i,-1)+2;
221  uint j = 0;
222  for (; j < RatedDimensions(i); j++)
223  m_ptrs[Index(i,j+1)] = Offset(i,j) + 2;
224  const unsigned char *tmp = Offset(i,-1) + 3 + (RatedDimensions(i)<<1);
225  uint len = RatingDescriptionLength(i);
226  m_ptrs[Index(i+1,-1)] = tmp + len;
227  }
228 
229  return true;
230 }
231 
233 {
234  return "ContentAdvisoryDescriptor::toString(): Not implemented";
235 }
236 
238 {
239  static const char* s_asd[] =
240  {
241  "48kbps", "44.1kbps", "32kbps", "Reserved",
242  "48kbps or 44.1kbps", "48kbps or 32kbps",
243  "44.1kbps or 32kbps", "48kbps or 44.1kbps or 32kbps"
244  };
245  return QString(s_asd[SampleRateCode()]);
246 }
247 
249 {
250  // cppcheck-suppress variableScope
251  static const char* s_ebr[19] =
252  {
253  "=32kbps", "=40kbps", "=48kbps", "=56kbps", "=64kbps",
254  "=80kbps", "=96kbps", "=112kbps", "=128kbps", "=160kbps",
255  "=192kbps", "=224kbps", "=256kbps", "=320kbps", "=384kbps",
256  "=448kbps", "=512kbps", "=576kbps", "=640kbps"
257  };
258  static const char* s_ubr[19] =
259  {
260  "<=32kbps", "<=40kbps", "<=48kbps", "<=56kbps", "<=64kbps",
261  "<=80kbps", "<=96kbps", "<=112kbps", "<=128kbps", "<=160kbps",
262  "<=192kbps","<=224kbps", "<=256kbps", "<=320kbps", "<=384kbps",
263  "<=448kbps","<=512kbps", "<=576kbps", "<=640kbps"
264  };
265 
266  if (BitRateCode() <= 18)
267  return QString(s_ebr[BitRateCode()]);
268  if ((BitRateCode() >= 32) && (BitRateCode() <= 50))
269  return QString(s_ubr[BitRateCode()-32]);
270  return QString("Unknown Bit Rate Code");
271 }
272 
274 {
275  static const char* s_sms[] =
276  {
277  "Not indicated",
278  "Not Dolby surround encoded",
279  "Dolby surround encoded",
280  "Reserved",
281  };
282  return QString(s_sms[SurroundMode()]);
283 }
284 
286 {
287  static const char* s_cs[] =
288  {
289  "1 + 1", "1/0", "2/0", "3/0",
290  "2/1", "3/1", "2/2 ", "3/2",
291  "1", "<= 2", "<= 3", "<= 4",
292  "<= 5", "<= 6", "Reserved", "Reserved"
293  };
294  return s_cs[Channels()];
295 }
296 
298 {
299  QString str;
300  str.append(QString("Audio Stream Descriptor "));
301  str.append(QString(" full_srv(%1) sample_rate(%2) bit_rate(%3, %4)\n")
302  .arg(static_cast<int>(FullService())).arg(SampleRateCodeString())
303  .arg(BitRateCodeString()).arg(BitRateCode()));
304  str.append(QString(" bsid(%1) bs_mode(%2) channels(%3) Dolby(%4)\n")
305  .arg(bsid()).arg(BasicServiceMode())
306  .arg(ChannelsString()).arg(SurroundModeString()));
307 
308  /*
309  str.append(QString(" language code: %1").arg(languageCode()));
310  if (0==channels()) {
311  str.append(QString(" language code 2: %1").arg(languageCode2()));
312  }
313  */
314 
315  if (BasicServiceMode() < 2)
316  str.append(QString(" mainID(%1) ").arg(MainID()));
317  else
318  str.append(QString(" associated_service(0x%1) ")
319  .arg(AServiceFlags(),0,16));
320 
321  if (TextLength())
322  {
323  str.append(QString("isLatin-1(%1) ")
324  .arg(IsTextLatin1() ? "true" : "false"));
325  str.append(QString("text_length(%1) ").arg(TextLength()));
326  str.append(QString("text(%1)").arg(Text()));
327  }
328  return str;
329 }
330 
336  void) const
337 {
338  return MultipleStringStructure(m_data + 2);
339 }
340 
346 {
347  QString str = "";
348  MultipleStringStructure mstr = LongChannelName();
349 
350  for (uint i = 0; i < mstr.StringCount(); i++)
351  str += mstr.GetFullString(i);
352 
353  return str;
354 }
355 
357 {
358  return QString("ExtendedChannelNameDescriptor: '%1'")
359  .arg(LongChannelNameString());
360 }
ISO 639-1 and ISO 639-2 support functions.
QString toString() const override
QString toString() const override
QString LongChannelNameString(void) const
Convenience function that returns a QString comprising a concatenation of all the segments in the Lon...
QString SampleRateCodeString(void) const
static guint32 * tmp
Definition: goom_core.cpp:30
MultipleStringStructure LongChannelName(void) const
Returns a MultipleStringStructure representing the long name of the associated channel.
QString toString() const override
uint StringCount(void) const
unsigned int uint
Definition: compat.h:140
QString CompressionTypeString(uint i, uint j) const
QString GetFullString(uint i) const
static QString Uncompressed(const unsigned char *buf, int len, int mode)
static uint maxPriority(const QMap< uint, uint > &langPrefs)
uint GetIndexOfBestMatch(QMap< uint, uint > &langPrefs) const
QString GetBestMatch(QMap< uint, uint > &langPrefs) const
QString toString() const override
QString BitRateCodeString(void) const
QString GetSegment(uint i, uint j) const
QString ChannelsString(void) const
QString atsc_huffman1_to_string(const unsigned char *compressed, uint size, uint table_index)
QString SurroundModeString(void) const
#define LOG(_MASK_, _LEVEL_, _QSTRING_)
Definition: mythlogging.h:23