AJA NTV2 SDK  18.0.0.2122
NTV2 SDK 18.0.0.2122
ntv2signalrouter.cpp
Go to the documentation of this file.
1 /* SPDX-License-Identifier: MIT */
7 #include "ntv2signalrouter.h"
8 #include "ntv2routingexpert.h"
9 #include "ntv2debug.h"
10 #include "ntv2utils.h"
11 #include "ntv2devicefeatures.hh"
12 #include "ntv2registerexpert.h"
13 #include "ajabase/system/debug.h"
14 #include "ajabase/common/common.h"
15 #include <memory.h>
16 #include <stdio.h>
17 #include <assert.h>
18 #include <algorithm>
19 
20 using namespace std;
21 
22 // Logging helpers
23 #define HEX16(__x__) "0x" << hex << setw(16) << setfill('0') << uint64_t(__x__) << dec
24 #define INSTP(_p_) HEX16(uint64_t(_p_))
25 #define SRiFAIL(__x__) AJA_sERROR (AJA_DebugUnit_RoutingGeneric, INSTP(this) << "::" << AJAFUNC << ": " << __x__)
26 #define SRiWARN(__x__) AJA_sWARNING(AJA_DebugUnit_RoutingGeneric, INSTP(this) << "::" << AJAFUNC << ": " << __x__)
27 #define SRiNOTE(__x__) AJA_sNOTICE (AJA_DebugUnit_RoutingGeneric, INSTP(this) << "::" << AJAFUNC << ": " << __x__)
28 #define SRiINFO(__x__) AJA_sINFO (AJA_DebugUnit_RoutingGeneric, INSTP(this) << "::" << AJAFUNC << ": " << __x__)
29 #define SRiDBG(__x__) AJA_sDEBUG (AJA_DebugUnit_RoutingGeneric, INSTP(this) << "::" << AJAFUNC << ": " << __x__)
30 #define SRFAIL(__x__) AJA_sERROR (AJA_DebugUnit_RoutingGeneric, AJAFUNC << ": " << __x__)
31 #define SRWARN(__x__) AJA_sWARNING(AJA_DebugUnit_RoutingGeneric, AJAFUNC << ": " << __x__)
32 #define SRNOTE(__x__) AJA_sNOTICE (AJA_DebugUnit_RoutingGeneric, AJAFUNC << ": " << __x__)
33 #define SRINFO(__x__) AJA_sINFO (AJA_DebugUnit_RoutingGeneric, AJAFUNC << ": " << __x__)
34 #define SRDBG(__x__) AJA_sDEBUG (AJA_DebugUnit_RoutingGeneric, AJAFUNC << ": " << __x__)
35 
36 static NTV2StringList & Tokenize (const string & inString, NTV2StringList & outTokens, const string & inDelimiters = " ", bool inTrimEmpty = false)
37 {
38  string::size_type pos (0), lastPos (0);
39  outTokens.clear ();
40  while (true)
41  {
42  pos = inString.find_first_of (inDelimiters, lastPos);
43  if (pos == string::npos)
44  {
45  pos = inString.length ();
46  if (pos != lastPos || !inTrimEmpty)
47  outTokens.push_back (NTV2StringList::value_type (inString.data () + lastPos, NTV2StringList::size_type(pos - lastPos)));
48  break;
49  }
50  else
51  {
52  if (pos != lastPos || !inTrimEmpty)
53  outTokens.push_back (NTV2StringList::value_type (inString.data () + lastPos, NTV2StringList::size_type(pos - lastPos)));
54  }
55  lastPos = pos + 1;
56  }
57  return outTokens;
58 }
59 
61 
62 bool CNTV2SignalRouter::AddConnection (const NTV2InputXptID inSignalInput, const NTV2OutputXptID inSignalOutput)
63 {
64  mConnections.insert (NTV2SignalConnection (inSignalInput, inSignalOutput));
65  SRiDBG(NTV2InputCrosspointIDToString(inSignalInput) << ", " << NTV2OutputCrosspointIDToString(inSignalOutput) << ": " << *this);
66  return true;
67 }
68 
69 
70 bool CNTV2SignalRouter::HasInput (const NTV2InputXptID inSignalInput) const
71 {
72  return mConnections.find (inSignalInput) != mConnections.end ();
73 }
74 
75 
77 {
78  NTV2XptConnectionsConstIter it(mConnections.find(inSignalInput));
79  return it != mConnections.end() ? it->second : NTV2_XptBlack;
80 }
81 
82 
83 bool CNTV2SignalRouter::HasConnection (const NTV2InputXptID inSignalInput, const NTV2OutputXptID inSignalOutput) const
84 {
85  NTV2XptConnectionsConstIter iter (mConnections.find (inSignalInput));
86  if (iter == mConnections.end())
87  return false;
88  return iter->second == inSignalOutput;
89 }
90 
91 
92 bool CNTV2SignalRouter::RemoveConnection (const NTV2InputXptID inSignalInput, const NTV2OutputXptID inSignalOutput)
93 {
94  NTV2XptConnectionsIter iter (mConnections.find (inSignalInput));
95  if (iter == mConnections.end())
96  return false; // Not in map
97  if (iter->second != inSignalOutput)
98  return false; // No match
99  mConnections.erase (iter);
100  return true;
101 }
102 
103 
104 static const ULWord sSignalRouterRegMasks[] = { 0x000000FF, 0x0000FF00, 0x00FF0000, 0xFF000000 };
105 static const ULWord sSignalRouterRegShifts[] = { 0, 8, 16, 24 };
106 
107 
109 {
110  Reset();
111  for (NTV2InputXptIDSetConstIter it(inInputs.begin()); it != inInputs.end(); ++it)
112  {
113  uint32_t regNum(0), maskNdx(0);
115  NTV2RegisterReadsConstIter iter (::FindFirstMatchingRegisterNumber(regNum, inRegReads));
116  if (iter == inRegReads.end())
117  continue;
118 
119  NTV2_ASSERT(iter->registerNumber == regNum);
120  NTV2_ASSERT(iter->registerMask == 0xFFFFFFFF);
121  NTV2_ASSERT(iter->registerShift == 0);
122  NTV2_ASSERT(maskNdx < 4);
123  const uint32_t regValue (iter->registerValue & sSignalRouterRegMasks[maskNdx]);
124  const NTV2OutputXptID outputXpt (NTV2OutputXptID(regValue >> sSignalRouterRegShifts[maskNdx]));
125  if (outputXpt != NTV2_XptBlack)
126  mConnections.insert(NTV2SignalConnection (*it, outputXpt));
127  } // for each NTV2InputXptID
128  return true;
129 }
130 
131 
133 {
134  outRegWrites.clear ();
135 
136  for (NTV2XptConnectionsConstIter iter (mConnections.begin ()); iter != mConnections.end (); ++iter)
137  {
138  const NTV2InputXptID inputXpt(iter->first);
139  const NTV2OutputXptID outputXpt(iter->second);
140  uint32_t regNum(0), ndx(999);
141 
142  if (!CNTV2RegisterExpert::GetCrosspointSelectGroupRegisterInfo (inputXpt, regNum, ndx) || !regNum || ndx > 3)
143  {
144  outRegWrites.clear();
145  return false;
146  }
147 
148  const NTV2RegInfo regInfo (regNum, outputXpt, sSignalRouterRegMasks[ndx], sSignalRouterRegShifts[ndx]);
149  try
150  {
151  outRegWrites.push_back (regInfo);
152  }
153  catch (const bad_alloc &)
154  {
155  outRegWrites.clear ();
156  return false;
157  }
158  }
159  SRiDBG(outRegWrites);
160  return true;
161 }
162 
163 
165  NTV2XptConnections & outChanged, NTV2XptConnections & outMissing) const
166 {
167  outNew.clear(); outChanged.clear(); outMissing.clear();
168  // Check that my connections are also in RHS:
169  for (NTV2XptConnectionsConstIter it(mConnections.begin()); it != mConnections.end(); ++it)
170  {
171  const NTV2SignalConnection & connection (*it);
172  const NTV2InputXptID inputXpt(connection.first);
173  const NTV2OutputXptID outputXpt(connection.second);
174  if (inRHS.HasConnection(inputXpt, outputXpt))
175  ;
176  else if (inRHS.HasInput(inputXpt))
177  outChanged.insert(NTV2Connection(inputXpt, inRHS.GetConnectedOutput(inputXpt))); // Connection changed from this
178  else
179  outNew.insert(connection); // Connection is new in me, not in RHS
180  }
181 
182  // Check that RHS' connections are also in me...
183  const NTV2XptConnections connectionsRHS(inRHS.GetConnections());
184  for (NTV2XptConnectionsConstIter it(connectionsRHS.begin()); it != connectionsRHS.end(); ++it)
185  {
186  const NTV2SignalConnection & connectionRHS (*it);
187  const NTV2InputXptID inputXpt(connectionRHS.first);
188  const NTV2OutputXptID outputXpt(connectionRHS.second);
189  NTV2XptConnectionsConstIter pFind (mConnections.find(inputXpt));
190  if (pFind == mConnections.end()) // If not found in me...
191  outMissing.insert(connectionRHS); // ...in RHS, but missing in me
192  else if (pFind->second != outputXpt) // If output xpt differs...
193  outChanged.insert(connectionRHS); // ...then 'connection' is changed (in RHS, not in me)
194  }
195 
196  return outNew.empty() && outChanged.empty() && outMissing.empty(); // Return true if identical
197 }
198 
199 
200 ostream & CNTV2SignalRouter::Print (ostream & oss, const bool inForRetailDisplay) const
201 {
202  if (inForRetailDisplay)
203  {
204  oss << mConnections.size() << " routing entries:" << endl;
205  for (NTV2XptConnectionsConstIter iter (mConnections.begin()); iter != mConnections.end(); ++iter)
206  oss << ::NTV2InputCrosspointIDToString(iter->first, inForRetailDisplay)
207  << " <== " << ::NTV2OutputCrosspointIDToString(iter->second, inForRetailDisplay) << endl;
208  }
209  else
210  oss << mConnections;
211  return oss;
212 }
213 
214 
215 bool CNTV2SignalRouter::PrintCode (string & outCode, const PrintCodeConfig & inConfig) const
216 {
217  return ToCodeString(outCode, mConnections, inConfig);
218 
219 } // PrintCode
220 
221 
222 bool CNTV2SignalRouter::ToCodeString (string & outCode, const NTV2XptConnections & inConnections,
223  const PrintCodeConfig & inConfig)
224 {
225  ostringstream oss;
226 
227  outCode.clear ();
228 
229  if (inConfig.mShowComments)
230  {
231  oss << inConfig.mPreCommentText << DEC(inConnections.size()) << " routing ";
232  oss << ((inConnections.size () == 1) ? "entry:" : "entries:");
233  oss << inConfig.mPostCommentText << inConfig.mLineBreakText;
234  }
235 
236  if (inConfig.mShowDeclarations)
237  {
238  if (inConfig.mUseRouter)
239  oss << inConfig.mPreClassText << "CNTV2SignalRouter" << inConfig.mPostClassText
240  << "\t"<< inConfig.mPreVariableText << inConfig.mRouterVarName<< inConfig.mPostVariableText;
241  else
242  oss << inConfig.mPreClassText << "CNTV2Card" << inConfig.mPostClassText
243  << "\t" << inConfig.mPreVariableText << inConfig.mDeviceVarName<< inConfig.mPostVariableText;
244  oss << ";" << inConfig.mLineBreakText;
245  }
246 
247  const string varName (inConfig.mUseRouter ? inConfig.mRouterVarName : inConfig.mDeviceVarName);
248  const string variableNameText (inConfig.mPreVariableText + varName + inConfig.mPostVariableText);
249  const string funcName (inConfig.mUseRouter ? "AddConnection" : "Connect");
250  const string functionCallText (inConfig.mPreFunctionText + funcName + inConfig.mPostFunctionText);
251  for (NTV2XptConnectionsConstIter iter (inConnections.begin ()); iter != inConnections.end (); ++iter)
252  {
253  const string inXptStr (inConfig.mPreXptText + ::NTV2InputCrosspointIDToString(iter->first, false) + inConfig.mPostXptText);
254  const string outXptStr (inConfig.mPreXptText + ::NTV2OutputCrosspointIDToString(iter->second, false) + inConfig.mPostXptText);
255 
256  oss << variableNameText << "." << functionCallText << " (" << inXptStr << ", " << outXptStr << ");";
257 
258  if (inConfig.mShowComments)
259  {
260  NTV2XptConnectionsConstIter pNew(inConfig.mNew.find(iter->first));
261  NTV2XptConnectionsConstIter pChanged(inConfig.mChanged.find(iter->first));
262  if (pNew != inConfig.mNew.end() && pNew->second == iter->second)
263  oss << inConfig.mFieldBreakText << inConfig.mPreCommentText << "New" << inConfig.mPostCommentText;
264  else if (pChanged != inConfig.mChanged.end() && pChanged->second != iter->second)
265  oss << inConfig.mFieldBreakText << inConfig.mPreCommentText << "Changed from "
266  << ::NTV2OutputCrosspointIDToString(pChanged->second, false) << inConfig.mPostCommentText;
267  }
268  oss << inConfig.mLineBreakText;
269  } // for each connection
270 
271  if (inConfig.mShowComments)
272  for (NTV2XptConnectionsConstIter pGone(inConfig.mMissing.begin()); pGone != inConfig.mMissing.end(); ++pGone)
273  if (inConnections.find(pGone->first) == inConnections.end())
274  {
275  if (inConfig.mUseRouter)
276  oss << inConfig.mPreCommentText << varName << "." << "RemoveConnection" << " ("
277  << ::NTV2InputCrosspointIDToString(pGone->first, false)
278  << ", " << ::NTV2OutputCrosspointIDToString(pGone->second, false)
279  << ");" << inConfig.mPostCommentText
280  << inConfig.mFieldBreakText << inConfig.mPreCommentText << "Deleted" << inConfig.mPostCommentText
281  << inConfig.mLineBreakText;
282  else
283  oss << inConfig.mPreCommentText << varName << "." << "Disconnect" << " ("
284  << ::NTV2InputCrosspointIDToString(pGone->first, false)
285  << ");" << inConfig.mPostCommentText << inConfig.mFieldBreakText
286  << inConfig.mPreCommentText
287  << "From " << ::NTV2OutputCrosspointIDToString(pGone->second, false)
288  << inConfig.mPostCommentText << inConfig.mLineBreakText;
289  }
290 
291  outCode = oss.str();
292  return true;
293 }
294 
295 
297  : mShowComments (true),
298  mShowDeclarations (true),
299  mUseRouter (false),
300  mPreCommentText ("// "),
301  mPostCommentText (),
302  mPreClassText (),
303  mPostClassText (),
304  mPreVariableText (),
305  mPostVariableText (),
306  mPreXptText (),
307  mPostXptText (),
308  mPreFunctionText (),
309  mPostFunctionText (),
310  mDeviceVarName ("device"),
311  mRouterVarName ("router"),
312  mLineBreakText ("\n"),
313  mFieldBreakText ("\t"),
314  mNew (),
315  mChanged (),
316  mMissing ()
317 {
318 }
319 
320 
321 bool CNTV2SignalRouter::Initialize (void) // STATIC
322 {
325  return pExpert ? true : false;
326 } // Initialize
327 
328 
329 bool CNTV2SignalRouter::Deinitialize (void) // STATIC
330 {
332 }
333 
334 
335 bool CNTV2SignalRouter::IsInitialized (void) // STATIC
336 {
339  return pExpert ? true : false;
340 }
341 
342 
344 {
347  return pExpert ? pExpert->InputXptToString(inInputXpt) : string();
348 }
349 
350 
352 {
355  return pExpert ? pExpert->OutputXptToString(inOutputXpt) : string();
356 }
357 
358 
360 {
363  return pExpert ? pExpert->StringToInputXpt(inStr) : NTV2_INPUT_CROSSPOINT_INVALID;
364 }
365 
366 
368 {
371  return pExpert ? pExpert->StringToOutputXpt(inStr) : NTV2_OUTPUT_CROSSPOINT_INVALID;
372 }
373 
374 
375 bool CNTV2SignalRouter::GetWidgetIDs (const NTV2DeviceID inDeviceID, NTV2WidgetIDSet & outWidgets) // STATIC
376 {
377  outWidgets.clear();
378  for (NTV2WidgetID widgetID(NTV2WidgetID(NTV2_WIDGET_FIRST)); NTV2_IS_VALID_WIDGET(widgetID); widgetID = NTV2WidgetID(widgetID+1))
379  if (::NTV2DeviceCanDoWidget (inDeviceID, widgetID))
380  outWidgets.insert(widgetID);
381  return !outWidgets.empty();
382 }
383 
384 
385 bool CNTV2SignalRouter::GetWidgetsForInput (const NTV2InputXptID inInputXpt, NTV2WidgetIDSet & outWidgetIDs) // STATIC
386 {
387  outWidgetIDs.clear();
390  return pExpert ? pExpert->GetWidgetsForInput(inInputXpt, outWidgetIDs) : false;
391 }
392 
393 
394 bool CNTV2SignalRouter::GetWidgetForInput (const NTV2InputXptID inInputXpt, NTV2WidgetID & outWidgetID, const NTV2DeviceID inDeviceID) // STATIC
395 {
396  outWidgetID = NTV2_WIDGET_INVALID;
397  NTV2WidgetIDSet wgts;
398  if (!GetWidgetsForInput(inInputXpt, wgts))
399  return false;
400  if (inDeviceID == DEVICE_ID_NOTFOUND)
401  outWidgetID = *(wgts.begin());
402  else
403  for (NTV2WidgetIDSetConstIter it(wgts.begin()); it != wgts.end(); ++it)
404  if (::NTV2DeviceCanDoWidget(inDeviceID, *it))
405  {
406  outWidgetID = *it;
407  break;
408  }
409  return outWidgetID != NTV2_WIDGET_INVALID;
410 }
411 
412 
413 bool CNTV2SignalRouter::GetWidgetsForOutput (const NTV2OutputXptID inOutputXpt, NTV2WidgetIDSet & outWidgetIDs) // STATIC
414 {
415  outWidgetIDs.clear();
418  return pExpert ? pExpert->GetWidgetsForOutput(inOutputXpt, outWidgetIDs) : false;
419 }
420 
421 
422 bool CNTV2SignalRouter::GetWidgetForOutput (const NTV2OutputXptID inOutputXpt, NTV2WidgetID & outWidgetID, const NTV2DeviceID inDeviceID) // STATIC
423 {
424  outWidgetID = NTV2_WIDGET_INVALID;
425  NTV2WidgetIDSet wgts;
426  {
428  if (!GetWidgetsForOutput(inOutputXpt, wgts))
429  return false;
430  }
431  if (inDeviceID == DEVICE_ID_NOTFOUND)
432  outWidgetID = *(wgts.begin());
433  else
434  for (NTV2WidgetIDSetConstIter it(wgts.begin()); it != wgts.end(); ++it)
435  if (::NTV2DeviceCanDoWidget(inDeviceID, *it))
436  {
437  outWidgetID = *it;
438  break;
439  }
440  return outWidgetID != NTV2_WIDGET_INVALID;
441 }
442 
443 
444 bool CNTV2SignalRouter::GetWidgetInputs (const NTV2WidgetID inWidgetID, NTV2InputXptIDSet & outInputs) // STATIC
445 {
446  outInputs.clear();
448  return pExpert ? pExpert->GetWidgetInputs(inWidgetID, outInputs) : false;
449 }
450 
451 
452 bool CNTV2SignalRouter::GetAllWidgetInputs (const NTV2DeviceID inDeviceID, NTV2InputXptIDSet & outInputs) // STATIC
453 {
454  outInputs.clear();
455  NTV2WidgetIDSet widgetIDs;
456  if (!GetWidgetIDs (inDeviceID, widgetIDs))
457  return false; // Fail
458 
459  for (NTV2WidgetIDSetConstIter iter(widgetIDs.begin()); iter != widgetIDs.end (); ++iter)
460  {
461  NTV2InputXptIDSet inputs;
462  CNTV2SignalRouter::GetWidgetInputs (*iter, inputs);
463  for (NTV2InputXptIDSetConstIter it(inputs.begin()); it != inputs.end(); ++it)
464  {
466  if (!::NTV2DeviceCanDo425Mux(inDeviceID))
467  if (!::NTV2DeviceCanDo8KVideo(inDeviceID))
468  if (::NTV2InputCrosspointIDToString(*it, false).find("DS2") != string::npos) // is DS2 input?
469  continue; // do not include FrameStore DS2 inputs for IP25G
470  outInputs.insert(*it);
471  }
472  }
473  return true;
474 }
475 
476 
477 bool CNTV2SignalRouter::GetAllRoutingRegInfos (const NTV2InputXptIDSet & inInputs, NTV2RegisterWrites & outRegInfos) // STATIC
478 {
479  outRegInfos.clear();
480 
481  set<uint32_t> regNums;
482  uint32_t regNum(0), maskNdx(0);
483  for (NTV2InputXptIDSetConstIter it(inInputs.begin()); it != inInputs.end(); ++it)
485  if (regNums.find(regNum) == regNums.end())
486  regNums.insert(regNum);
487  for (set<uint32_t>::const_iterator iter(regNums.begin()); iter != regNums.end(); ++iter)
488  outRegInfos.push_back(NTV2RegInfo(*iter));
489 
490  return true;
491 }
492 
493 
494 bool CNTV2SignalRouter::GetWidgetOutputs (const NTV2WidgetID inWidgetID, NTV2OutputXptIDSet & outOutputs) // STATIC
495 {
496  outOutputs.clear();
498  return pExpert ? pExpert->GetWidgetOutputs(inWidgetID, outOutputs) : false;
499 }
500 
501 bool CNTV2SignalRouter::GetAllWidgetOutputs (const NTV2DeviceID inDeviceID, NTV2OutputXptIDSet & outOutputs) // STATIC
502 {
503  outOutputs.clear();
504  NTV2WidgetIDSet widgetIDs;
505  if (!GetWidgetIDs (inDeviceID, widgetIDs))
506  return false; // Fail
507 
508  for (NTV2WidgetIDSetConstIter iter(widgetIDs.begin()); iter != widgetIDs.end (); ++iter)
509  {
510  NTV2OutputXptIDSet outputs;
511  CNTV2SignalRouter::GetWidgetOutputs (*iter, outputs);
512  for (NTV2OutputXptIDSetConstIter it(outputs.begin()); it != outputs.end(); ++it)
513  {
515  if (!::NTV2DeviceCanDo425Mux(inDeviceID))
516  if (!::NTV2DeviceCanDo8KVideo(inDeviceID))
517  if (::NTV2OutputCrosspointIDToString(*it, false).find("DS2") != string::npos) // is DS2 output?
518  continue; // do not include FrameStore DS2 outputs for IP25G
519  outOutputs.insert(*it);
520  }
521  }
522  return true;
523 }
524 
526 {
528  return pExpert ? pExpert->IsRGBOnlyInputXpt(inInputXpt) : false;
529 }
530 
532 {
534  return pExpert ? pExpert->IsYUVOnlyInputXpt(inInputXpt) : false;
535 }
536 
538 {
540  return pExpert ? pExpert->IsKeyInputXpt(inInputXpt) : false;
541 }
542 
544 {
546  if (pExpert)
547  return pExpert->WidgetIDToChannel(inWidgetID);
548  return NTV2_CHANNEL_INVALID;
549 }
550 
552 {
554  if (pExpert)
555  return pExpert->WidgetIDFromTypeAndChannel(inWidgetType, inChannel);
556  return NTV2_WIDGET_INVALID;
557 }
558 
560 {
562  if (pExpert)
563  return pExpert->WidgetIDToType(inWidgetID);
564  return NTV2WidgetType_Invalid;
565 }
566 
568 {
570  return pExpert ? pExpert->IsSDIWidget(inWidgetType) : false;
571 }
572 
574 {
576  return pExpert ? pExpert->IsSDIInWidget(inWidgetType) : false;
577 }
578 
580 {
582  return pExpert ? pExpert->IsSDIOutWidget(inWidgetType) : false;
583 }
584 
586 {
588  return pExpert ? pExpert->Is3GSDIWidget(inWidgetType) : false;
589 }
590 
592 {
594  return pExpert ? pExpert->Is12GSDIWidget(inWidgetType) : false;
595 }
596 
598 {
600  return pExpert ? pExpert->IsDualLinkWidget(inWidgetType) : false;
601 }
602 
604 {
606  return pExpert ? pExpert->IsDualLinkInWidget(inWidgetType) : false;
607 }
608 
610 {
612  return pExpert ? pExpert->IsDualLinkOutWidget(inWidgetType) : false;
613 }
614 
616 {
618  return pExpert ? pExpert->IsHDMIWidget(inWidgetType) : false;
619 }
620 
622 {
624  return pExpert ? pExpert->IsHDMIInWidget(inWidgetType) : false;
625 }
626 
628 {
630  return pExpert ? pExpert->IsHDMIOutWidget(inWidgetType) : false;
631 }
632 
633 bool CNTV2SignalRouter::GetConnectionsFromRegs (const NTV2InputXptIDSet & inInputXptIDs, const NTV2RegisterReads & inRegValues, NTV2XptConnections & outConnections)
634 {
635  outConnections.clear();
636  for (NTV2InputXptIDSetConstIter it(inInputXptIDs.begin()); it != inInputXptIDs.end(); ++it)
637  {
638  uint32_t regNum(0), maskNdx(0);
640  NTV2RegisterReadsConstIter iter (::FindFirstMatchingRegisterNumber(regNum, inRegValues));
641  if (iter == inRegValues.end())
642  continue;
643 
644  if (iter->registerNumber != regNum)
645  return false; // Register numbers must match here
646  if (iter->registerMask != 0xFFFFFFFF)
647  return false; // Mask must be 0xFFFFFFFF
648  if (iter->registerShift)
649  return false; // Shift must be zero
650  NTV2_ASSERT(maskNdx < 4);
651  const uint32_t regValue (iter->registerValue & sSignalRouterRegMasks[maskNdx]);
652  const NTV2OutputXptID outputXpt (NTV2OutputXptID(regValue >> sSignalRouterRegShifts[maskNdx]));
653  if (outputXpt != NTV2_XptBlack)
654  outConnections.insert(NTV2SignalConnection (*it, outputXpt));
655  } // for each NTV2InputXptID
656  return true;
657 }
658 
659 
661  const NTV2XptConnections & inRHS,
662  NTV2XptConnections & outNew,
663  NTV2XptConnections & outMissing)
664 {
665  outNew.clear(); outMissing.clear();
666  // Check that LHS connections are also in RHS:
667  for (NTV2XptConnectionsConstIter it(inLHS.begin()); it != inLHS.end(); ++it)
668  {
669  const NTV2SignalConnection & LHSconnection(*it);
670  const NTV2InputXptID inputXpt(LHSconnection.first);
671  const NTV2OutputXptID outputXpt(LHSconnection.second);
672  NTV2XptConnectionsConstIter RHSit(inRHS.find(inputXpt));
673  if (RHSit == inRHS.end())
674  outMissing.insert(LHSconnection); // LHSConnection's inputXpt missing from RHS
675  else if (RHSit->second == outputXpt)
676  ; // LHS's input xpt connected to same output xpt as RHS
677  else
678  {
679  outMissing.insert(LHSconnection); // LHS connection missing from RHS
680  outNew.insert(*RHSit); // RHS connection is new
681  }
682  }
683 
684  // Check that RHS connections are also in LHS...
685  for (NTV2XptConnectionsConstIter it(inRHS.begin()); it != inRHS.end(); ++it)
686  {
687  const NTV2SignalConnection & connectionRHS (*it);
688  const NTV2InputXptID inputXpt(connectionRHS.first);
689  const NTV2OutputXptID outputXpt(connectionRHS.second);
690  NTV2XptConnectionsConstIter LHSit(inLHS.find(inputXpt));
691  if (LHSit == inLHS.end()) // If RHS input xpt not in LHS...
692  outNew.insert(connectionRHS); // ...then RHS connection is new
693  else if (LHSit->second != outputXpt) // Else if output xpt changed...
694  // Should've already been handled in previous for loop
695  NTV2_ASSERT(outMissing.find(LHSit->first) != outMissing.end() && outNew.find(LHSit->first) != outNew.end());
696  }
697 
698  return outNew.empty() && outMissing.empty(); // Return true if identical
699 }
700 
701 
702 bool CNTV2SignalRouter::CreateFromString (const string & inString, NTV2XptConnections & outConnections) // STATIC
703 {
704  NTV2StringList lines;
705  string stringToParse(inString); aja::strip(aja::lower(stringToParse));
706  aja::replace(stringToParse, " ", "");
707  aja::replace(stringToParse, "\t", "");
708  aja::replace(stringToParse, "&lt;","<"); // in case uuencoded
709 
710  outConnections.clear();
711  if (Tokenize(stringToParse, lines, "\n\r", true).empty()) // Split the string at line breaks
712  {
713  SRWARN("No lines resulted from input string '" << stringToParse << "'");
714  return true; // Nothing there
715  }
716 
717  if (lines.front().find("<==") != string::npos)
718  {
719 // SRDBG(lines.size() << " lines");
720  for (NTV2StringListConstIter pEachLine(lines.begin()); pEachLine != lines.end(); ++pEachLine)
721  {
722 // SRDBG(" line '" << *pEachLine << "'");
723  size_t pos (pEachLine->find("<=="));
724  if (pos == string::npos)
725  {SRFAIL("Parse error: '<==' missing in line '" << *pEachLine << "'"); return false;}
726  string leftPiece (pEachLine->substr(0, pos)); aja::strip(leftPiece);
727  string rightPiece (pEachLine->substr(pos + 3, pEachLine->length())); aja::strip(rightPiece);
728  NTV2InputXptID inputXpt (StringToNTV2InputCrosspointID(leftPiece));
729  NTV2OutputXptID outputXpt (StringToNTV2OutputCrosspointID(rightPiece));
730  //SRDBG(" L'" << leftPiece << "', R'" << rightPiece << "'");
731  if (inputXpt == NTV2_INPUT_CROSSPOINT_INVALID)
732  {SRFAIL("Parse error: invalid input crosspoint from '" << leftPiece << "' from line '" << *pEachLine << "'"); return false;}
733  if (outConnections.find(inputXpt) != outConnections.end())
734  SRWARN("Overwriting " << ::NTV2InputCrosspointIDToString(inputXpt) << "-" << ::NTV2OutputCrosspointIDToString(outConnections[inputXpt])
735  << " with " << ::NTV2InputCrosspointIDToString(inputXpt) << "-" << ::NTV2OutputCrosspointIDToString(outputXpt));
736  outConnections.insert(NTV2Connection(inputXpt, outputXpt));
737  } // for each line
738  }
739  else if (lines.front().find("connect(") != string::npos)
740  {
741  for (NTV2StringListConstIter pLine(lines.begin()); pLine != lines.end(); ++pLine)
742  {
743  string line(*pLine); aja::strip(line);
744  if (line.empty())
745  continue;
746  if (line.find("//") == 0) // starts with "//"
747  continue;
748 // SRDBG(" line '" << line << "'");
749  size_t openParenPos(line.find("(")), closedParenPos(line.find(");"));
750  if (openParenPos == string::npos || closedParenPos == string::npos || openParenPos > closedParenPos)
751  {SRFAIL("Parse error: '(' or ');' missing in line '" << line << "'"); return false;}
752  string remainder(line.substr(openParenPos+1, closedParenPos - openParenPos - 1));
753  NTV2StringList xptNames;
754  aja::split(remainder, ',', xptNames);
755  if (xptNames.size() < 2 || xptNames.size() > 2)
756  {SRFAIL("Parse error: " << DEC(xptNames.size()) << " 'Connect' parameter(s) found, expected 2"); return false;}
757  NTV2InputXptID inputXpt (StringToNTV2InputCrosspointID(xptNames.at(0)));
758  NTV2OutputXptID outputXpt (StringToNTV2OutputCrosspointID(xptNames.at(1)));
759  //SRDBG(" L'" << xptNames.at(0) << "', R'" << xptNames.at(1) << "'");
760  if (inputXpt == NTV2_INPUT_CROSSPOINT_INVALID)
761  {SRFAIL("Parse error: invalid input crosspoint from '" << xptNames.at(0) << "' from line '" << *pLine << "'"); return false;}
762  if (outputXpt == NTV2_OUTPUT_CROSSPOINT_INVALID)
763  {SRFAIL("Parse error: invalid output crosspoint from '" << xptNames.at(1) << "' from line '" << *pLine << "'"); return false;}
764  if (outConnections.find(inputXpt) != outConnections.end())
765  SRWARN("Overwriting " << ::NTV2InputCrosspointIDToString(inputXpt) << "-" << ::NTV2OutputCrosspointIDToString(outConnections[inputXpt])
766  << " with " << ::NTV2InputCrosspointIDToString(inputXpt) << "-" << ::NTV2OutputCrosspointIDToString(outputXpt));
767  outConnections.insert(NTV2Connection(inputXpt, outputXpt));
768  } // for each line
769  }
770  else
771  {SRFAIL("Unable to parse '" << lines.front() << "' -- expected '.contains(' or '<=='"); return false;}
772  SRINFO(DEC(outConnections.size()) << " connection(s) created from input string");
773  return true;
774 }
775 
776 
777 bool CNTV2SignalRouter::CreateFromString (const string & inString, CNTV2SignalRouter & outRouter) // STATIC
778 {
780  outRouter.Reset();
781  if (!CreateFromString(inString, connections))
782  return false;
783  return outRouter.ResetFrom(connections);
784 }
785 
787 
788 
789 
791 
792 NTV2InputXptID GetFrameStoreInputXptFromChannel (const NTV2Channel inChannel, const bool inIsBInput)
793 {
798  if (NTV2_IS_VALID_CHANNEL (inChannel))
799  return inIsBInput ? gFrameBufferBInputs [inChannel] : gFrameBufferInputs [inChannel];
800  else
802 }
803 
804 
805 NTV2InputXptID GetCSCInputXptFromChannel (const NTV2Channel inChannel, const bool inIsKeyInput)
806 {
811  if (NTV2_IS_VALID_CHANNEL(inChannel))
812  return inIsKeyInput ? gCSCKeyInput[inChannel] : gCSCVideoInput[inChannel];
813  else
815 }
816 
817 
819 {
822  return NTV2_IS_VALID_CHANNEL(inLUT) ? gLUTInput[inLUT] : NTV2_INPUT_CROSSPOINT_INVALID;
823 }
824 
825 
826 NTV2InputXptID GetDLInInputXptFromChannel (const NTV2Channel inChannel, const bool inLinkB)
827 {
832  if (NTV2_IS_VALID_CHANNEL(inChannel))
833  return inLinkB ? gDLBInputs[inChannel] : gDLInputs[inChannel];
834  else
836 }
837 
839 {
842  if (NTV2_IS_VALID_CHANNEL(inChannel))
843  return gDLOutInputs[inChannel];
844  else
846 }
847 
848 
849 NTV2OutputXptID GetCSCOutputXptFromChannel (const NTV2Channel inChannel, const bool inIsKey, const bool inIsRGB)
850 {
857  if (NTV2_IS_VALID_CHANNEL(inChannel))
858  {
859  if (inIsKey)
860  return gCSCKeyOutputs[inChannel];
861  else
862  return inIsRGB ? gCSCRGBOutputs[inChannel] : gCSCYUVOutputs[inChannel];
863  }
864  else
866 }
867 
869 {
872  return NTV2_IS_VALID_CHANNEL(inLUT) ? gLUTRGBOutputs[inLUT] : NTV2_OUTPUT_CROSSPOINT_INVALID;
873 }
874 
875 NTV2OutputXptID GetFrameStoreOutputXptFromChannel (const NTV2Channel inChannel, const bool inIsRGB, const bool inIs425)
876 {
885  if (NTV2_IS_VALID_CHANNEL(inChannel))
886  if (inIs425)
887  return inIsRGB ? gFrameBufferRGB425Outputs[inChannel] : gFrameBufferYUV425Outputs[inChannel];
888  else
889  return inIsRGB ? gFrameBufferRGBOutputs[inChannel] : gFrameBufferYUVOutputs[inChannel];
890  else
892 }
893 
894 
895 NTV2OutputXptID GetInputSourceOutputXpt (const NTV2InputSource inInputSource, const bool inIsSDI_DS2, const bool inIsHDMI_RGB, const UWord inHDMI_Quadrant)
896 {
897  static const NTV2OutputXptID gHDMIInputOutputs [4][4] = { { NTV2_XptHDMIIn1, NTV2_XptHDMIIn1Q2, NTV2_XptHDMIIn1Q3, NTV2_XptHDMIIn1Q4 },
901  static const NTV2OutputXptID gHDMIInputRGBOutputs [4][4] = { { NTV2_XptHDMIIn1RGB, NTV2_XptHDMIIn1Q2RGB, NTV2_XptHDMIIn1Q3RGB, NTV2_XptHDMIIn1Q4RGB },
905 
906  if (NTV2_INPUT_SOURCE_IS_SDI (inInputSource))
908  else if (NTV2_INPUT_SOURCE_IS_HDMI (inInputSource))
909  {
910  NTV2Channel channel = ::NTV2InputSourceToChannel (inInputSource);
911  if (inHDMI_Quadrant < 4)
912  return inIsHDMI_RGB ? gHDMIInputRGBOutputs [channel][inHDMI_Quadrant] : gHDMIInputOutputs [channel][inHDMI_Quadrant];
913  else
915  }
916  else if (NTV2_INPUT_SOURCE_IS_ANALOG (inInputSource))
917  return NTV2_XptAnalogIn;
918  else
920 }
921 
922 
923 NTV2OutputXptID GetSDIInputOutputXptFromChannel (const NTV2Channel inChannel, const bool inIsDS2)
924 {
925  static const NTV2OutputXptID gSDIInputOutputs [] = { NTV2_XptSDIIn1, NTV2_XptSDIIn2, NTV2_XptSDIIn3, NTV2_XptSDIIn4,
929  if (NTV2_IS_VALID_CHANNEL(inChannel))
930  return inIsDS2 ? gSDIInputDS2Outputs[inChannel] : gSDIInputOutputs[inChannel];
931  else
933 }
934 
935 NTV2OutputXptID GetDLOutOutputXptFromChannel(const NTV2Channel inChannel, const bool inIsLinkB)
936 {
941  if (NTV2_IS_VALID_CHANNEL(inChannel))
942  return inIsLinkB ? gDLOutDS2Outputs[inChannel] : gDLOutOutputs[inChannel];
943  else
945 }
946 
948 {
951  if (NTV2_IS_VALID_CHANNEL(inChannel))
952  return gDLInOutputs[inChannel];
953  else
955 }
956 
957 
958 NTV2InputXptID GetOutputDestInputXpt (const NTV2OutputDestination inOutputDest, const bool inIsSDI_DS2, const UWord inHDMI_Quadrant)
959 {
961  if (NTV2_OUTPUT_DEST_IS_SDI(inOutputDest))
962  return ::GetSDIOutputInputXpt (::NTV2OutputDestinationToChannel(inOutputDest), inIsSDI_DS2);
963  else if (NTV2_OUTPUT_DEST_IS_HDMI(inOutputDest))
964  return inHDMI_Quadrant > 3 ? NTV2_XptHDMIOutInput : gHDMIOutputInputs[inHDMI_Quadrant];
965  else if (NTV2_OUTPUT_DEST_IS_ANALOG(inOutputDest))
966  return NTV2_XptAnalogOutInput;
967  else
969 }
970 
971 
972 NTV2InputXptID GetSDIOutputInputXpt (const NTV2Channel inChannel, const bool inIsDS2)
973 {
978  if (NTV2_IS_VALID_CHANNEL (inChannel))
979  return inIsDS2 ? gSDIOutputDS2Inputs [inChannel] : gSDIOutputInputs [inChannel];
980  else
982 }
983 
984 
985 NTV2OutputXptID GetMixerOutputXptFromChannel (const NTV2Channel inChannel, const bool inIsKey)
986 {
991  if (NTV2_IS_VALID_CHANNEL(inChannel))
992  return inIsKey ? gMixerKeyYUVOutputs[inChannel] : gMixerVidYUVOutputs[inChannel];
993  else
995 }
996 
997 
998 NTV2InputXptID GetMixerFGInputXpt (const NTV2Channel inChannel, const bool inIsKey)
999 {
1004  if (NTV2_IS_VALID_CHANNEL(inChannel))
1005  return inIsKey ? gMixerFGKeyInputs[inChannel] : gMixerFGVideoInputs[inChannel];
1006  else
1008 }
1009 
1010 
1011 NTV2InputXptID GetMixerBGInputXpt (const NTV2Channel inChannel, const bool inIsKey)
1012 {
1017  if (NTV2_IS_VALID_CHANNEL(inChannel))
1018  return inIsKey ? gMixerBGKeyInputs[inChannel] : gMixerBGVideoInputs[inChannel];
1019  else
1021 }
1022 
1023 NTV2InputXptID GetTSIMuxInputXptFromChannel (const NTV2Channel inChannel, const bool inLinkB)
1024 {
1029  if (NTV2_IS_VALID_CHANNEL(inChannel))
1030  return inLinkB ? gDLBInputs[inChannel] : gDLInputs[inChannel];
1031  else
1033 }
1034 
1035 NTV2OutputXptID GetTSIMuxOutputXptFromChannel (const NTV2Channel inChannel, const bool inLinkB, const bool inIsRGB)
1036 {
1045  if (NTV2_IS_VALID_CHANNEL(inChannel))
1046  {
1047  if (inLinkB)
1048  return inIsRGB ? gMuxBRGBOutputs[inChannel] : gMuxBYUVOutputs[inChannel];
1049  else
1050  return inIsRGB ? gMuxARGBOutputs[inChannel] : gMuxAYUVOutputs[inChannel];
1051  }
1052  else
1054 }
1056 
1057 
1058 // static
1059 bool CNTV2SignalRouter::GetRouteROMInfoFromReg (const ULWord inRegNum, const ULWord inRegVal,
1060  NTV2InputXptID & outInputXpt, NTV2OutputXptIDSet & outOutputXpts, const bool inAppendOutputXpts)
1061 {
1062  static const ULWord firstROMReg(kRegFirstValidXptROMRegister);
1063  static const ULWord firstInpXpt(NTV2_FIRST_INPUT_CROSSPOINT);
1064  if (!inAppendOutputXpts)
1065  outOutputXpts.clear();
1066  outInputXpt = NTV2_INPUT_CROSSPOINT_INVALID;
1067  if (inRegNum < uint32_t(kRegFirstValidXptROMRegister))
1068  return false;
1069  if (inRegNum >= uint32_t(kRegInvalidValidXptROMRegister))
1070  return false;
1071 
1072  const ULWord regOffset(inRegNum - firstROMReg);
1073  const ULWord bitOffset((regOffset % 4) * 32);
1074  outInputXpt = NTV2InputXptID(firstInpXpt + regOffset / 4UL); // 4 regs per inputXpt
1075  if (!inRegVal)
1076  return true; // No bits set
1077 
1079  NTV2_ASSERT(pExpert);
1080  for (UWord bitNdx(0); bitNdx < 32; bitNdx++)
1081  if (inRegVal & ULWord(1UL << bitNdx))
1082  {
1083  const NTV2OutputXptID yuvOutputXpt (NTV2OutputXptID((bitOffset + bitNdx) & 0x0000007F));
1084  const NTV2OutputXptID rgbOutputXpt (NTV2OutputXptID(yuvOutputXpt | 0x80));
1085  if (pExpert && pExpert->IsOutputXptValid(yuvOutputXpt))
1086  outOutputXpts.insert(yuvOutputXpt);
1087  if (pExpert && pExpert->IsOutputXptValid(rgbOutputXpt))
1088  outOutputXpts.insert(rgbOutputXpt);
1089  }
1090  return true;
1091 }
1092 
1093 // static
1095 {
1096  outConnections.clear();
1097  for (NTV2RegReadsConstIter iter(inROMRegs.begin()); iter != inROMRegs.end(); ++iter)
1098  {
1099  if (iter->registerNumber < kRegFirstValidXptROMRegister || iter->registerNumber >= kRegInvalidValidXptROMRegister)
1100  continue; // Skip -- not a ROM reg
1102  NTV2OutputXptIDSet outputXpts;
1103  if (GetRouteROMInfoFromReg (iter->registerNumber, iter->registerValue, inputXpt, outputXpts, true))
1104  for (NTV2OutputXptIDSetConstIter it(outputXpts.begin()); it != outputXpts.end(); ++it)
1105  outConnections.insert(NTV2Connection(inputXpt, *it));
1106  }
1107  return !outConnections.empty();
1108 }
1109 
1110 // static
1112 {
1113  outROMRegs.clear();
1114  for (uint32_t regNum(kRegFirstValidXptROMRegister); regNum < kRegInvalidValidXptROMRegister; regNum++)
1115  outROMRegs.push_back(NTV2RegInfo(regNum));
1116  return true;
1117 }
1118 
1119 
1121 
1122 ostream & operator << (ostream & oss, const CNTV2SignalRouter & inObj)
1123 {
1124  return inObj.Print(oss);
1125 }
1126 
1127 
1128 ostream & operator << (ostream & oss, const NTV2OutputXptIDSet & inObj)
1129 {
1130  NTV2OutputXptIDSetConstIter iter(inObj.begin());
1131  while (iter != inObj.end())
1132  {
1133  oss << ::NTV2OutputCrosspointIDToString(*iter, false);
1134  if (++iter == inObj.end())
1135  break;
1136  oss << ", ";
1137  }
1138  return oss;
1139 }
1140 
1141 ostream & operator << (ostream & oss, const NTV2InputXptIDSet & inObj)
1142 {
1143  NTV2InputXptIDSetConstIter iter(inObj.begin());
1144  while (iter != inObj.end())
1145  {
1146  oss << ::NTV2InputCrosspointIDToString(*iter, false);
1147  if (++iter == inObj.end())
1148  break;
1149  oss << ", ";
1150  }
1151  return oss;
1152 }
1153 
1155 {
1156  registerNum = inRHS.registerNumber;
1157  mask = inRHS.registerMask;
1158  shift = inRHS.registerShift;
1159  value = inRHS.registerValue;
1160  return *this;
1161 }
1162 
1163 ostream & operator << (ostream & inOutStream, const NTV2WidgetIDSet & inObj)
1164 {
1165  for (NTV2WidgetIDSetConstIter iter (inObj.begin ()); iter != inObj.end (); )
1166  {
1167  inOutStream << ::NTV2WidgetIDToString (*iter, true);
1168  if (++iter != inObj.end ())
1169  inOutStream << ",";
1170  }
1171  return inOutStream;
1172 }
1173 
1174 ostream & operator << (ostream & oss, const NTV2XptConnection & inObj)
1175 {
1176  oss << ::NTV2InputCrosspointIDToString(inObj.first) << " <== " << ::NTV2OutputCrosspointIDToString(inObj.second);
1177  return oss;
1178 }
1179 
1180 ostream & operator << (ostream & oss, const NTV2XptConnections & inObj)
1181 {
1182  for (NTV2XptConnectionsConstIter it(inObj.begin()); it != inObj.end(); )
1183  {
1184  oss << *it;
1185  if (++it != inObj.end())
1186  oss << endl;
1187  }
1188  return oss;
1189 }
1190 
NTV2Channel NTV2InputSourceToChannel(const NTV2InputSource inInputSource)
Converts a given NTV2InputSource to its equivalent NTV2Channel value.
Definition: ntv2utils.cpp:5047
NTV2XptConnections::const_iterator NTV2XptConnectionsConstIter
Everything needed to call CNTV2Card::ReadRegister or CNTV2Card::WriteRegister functions.
static bool Deinitialize(void)
Explicitly deinitializes and deallocates the Routing Expert singleton.
static bool IsKeyInputXpt(const NTV2InputXptID inInputXpt)
NTV2OutputXptID GetDLInOutputXptFromChannel(const NTV2Channel inChannel)
static const ULWord sSignalRouterRegShifts[]
NTV2InputXptIDSet::const_iterator NTV2InputXptIDSetConstIter
A const iterator for iterating over an NTV2InputXptIDSet.
std::string mPostCommentText
Comment postfix text.
#define SRINFO(__x__)
Declares the AJAMemory class.
std::string NTV2WidgetIDToString(const NTV2WidgetID inValue, const bool inCompactDisplay=false)
Definition: ntv2utils.cpp:6162
virtual void Reset(void)
Resets me, erasing any/all existing connections.
ULWord registerMask
My register mask value to use in a ReadRegister or WriteRegister call.
NTV2RegWritesConstIter NTV2RegReadsConstIter
A handy const (read-only) iterator for iterating over the contents of an NTV2RegisterReads instance...
static bool GetPossibleConnections(const NTV2RegReads &inROMRegisters, NTV2PossibleConnections &outConnections)
Answers with the implemented crosspoint connections as obtained from the given ROM registers...
virtual bool AddConnection(const NTV2InputXptID inSignalInput, const NTV2OutputXptID inSignalOutput=NTV2_XptBlack)
Adds a connection between a widget&#39;s signal input (sink) and another widget&#39;s signal output (source)...
NTV2OutputXptID GetDLOutOutputXptFromChannel(const NTV2Channel inChannel, const bool inIsLinkB)
Declares CNTV2SignalRouter class.
static bool GetConnectionsFromRegs(const NTV2InputXptIDSet &inInputXptIDs, const NTV2RegisterReads &inRegValues, NTV2XptConnections &outConnections)
Converts a set of crosspoint registers into a set of crosspoint connections.
virtual bool HasConnection(const NTV2InputXptID inSignalInput, const NTV2OutputXptID inSignalOutput) const
Answers true if I contain a connection between the specified input (signal sink) and output (signal s...
NTV2OutputDestination
Identifies a specific video output destination.
Definition: ntv2enums.h:1324
Declares the AJADebug class.
ostream & operator<<(ostream &oss, const CNTV2SignalRouter &inObj)
NTV2OutputXptID GetLUTOutputXptFromChannel(const NTV2Channel inLUT)
static bool IsHDMIOutWidgetType(const NTV2WidgetType inWidgetType)
NTV2InputXptID GetDLOutInputXptFromChannel(const NTV2Channel inChannel)
bool NTV2DeviceCanDo425Mux(const NTV2DeviceID inDeviceID)
virtual bool GetRegisterWrites(NTV2RegisterWrites &outRegWrites) const
Returns a sequence of NTV2RegInfo values that can be written to an NTV2 device using its WriteRegiste...
static std::string NTV2InputCrosspointIDToString(const NTV2InputXptID inInputXpt)
Returns a string containing the most compact human-readable form for a given input crosspoint...
if(!(riid==IID_IUnknown) &&!(riid==IID_IClassFactory))
Definition: dllentry.cpp:196
static bool Initialize(void)
Explicitly allocates and initializes the Routing Expert singleton.
I am a reference-counted pointer template class. I am intended to be a proxy for an underlying object...
Definition: ajarefptr.h:89
std::string mFieldBreakText
Text to use for field breaks.
static bool CompareConnections(const NTV2XptConnections &inLHS, const NTV2XptConnections &inRHS, NTV2XptConnections &outNew, NTV2XptConnections &outRemoved)
Compares two sets of crosspoint connections.
static bool GetWidgetOutputs(const NTV2WidgetID inWidgetID, NTV2OutputXptIDSet &outOutputs)
Returns the output crosspoints known to be "owned" by the given widget.
static bool IsSDIOutputWidgetType(const NTV2WidgetType inWidgetType)
NTV2XptConnections mNew
Optional, to show new connections.
static bool Is12GSDIWidgetType(const NTV2WidgetType inWidgetType)
Definition: json.hpp:5362
std::string mRouterVarName
Name to use for CNTV2SignalRouter variable.
virtual NTV2XptConnections GetConnections(void) const
NTV2InputXptID GetMixerFGInputXpt(const NTV2Channel inChannel, const bool inIsKey)
#define false
std::pair< NTV2InputXptID, NTV2OutputXptID > NTV2Connection
This links an NTV2InputXptID and an NTV2OutputXptID.
uint32_t ULWord
Definition: ajatypes.h:223
NTV2Channel
These enum values are mostly used to identify a specific widget_framestore. They&#39;re also commonly use...
Definition: ntv2enums.h:1357
NTV2OutputXptIDSet::const_iterator NTV2OutputXptIDSetConstIter
A const iterator for iterating over an NTV2OutputXptIDSet.
This class is a collection of widget input-to-output connections that can be applied all-at-once to a...
static bool CreateFromString(const std::string &inString, NTV2XptConnections &outConnections)
Decodes a given string into a map of crosspoint connections.
NTV2WidgetType
Definition: ntv2enums.h:3047
#define NTV2_OUTPUT_DEST_IS_HDMI(_dest_)
Definition: ntv2enums.h:1344
std::string mDeviceVarName
Name to use for CNTV2Card variable.
static bool IsInitialized(void)
#define NTV2_ASSERT(_expr_)
Definition: ajatypes.h:476
NTV2RegWritesConstIter NTV2RegisterReadsConstIter
Declares RoutingExpert class used by CNTV2SignalRouter.
NTV2Channel NTV2OutputDestinationToChannel(const NTV2OutputDestination inOutputDest)
Converts a given NTV2OutputDestination to its equivalent NTV2Channel value.
Definition: ntv2utils.cpp:5155
bool mShowDeclarations
If true, show variable declarations in the generated code.
std::string NTV2InputCrosspointIDToString(const NTV2InputCrosspointID inValue, const bool inForRetailDisplay=false)
Definition: ntv2utils.cpp:5814
#define true
static bool GetRouteROMInfoFromReg(const ULWord inROMRegNum, const ULWord inROMRegValue, NTV2InputXptID &outInputXpt, NTV2OutputXptIDSet &outOutputXpts, const bool inAppendOutputXpts=false)
Answers with the NTV2InputXptID and NTV2OutputXptIDSet for the given ROM register value...
NTV2InputXptID GetFrameStoreInputXptFromChannel(const NTV2Channel inChannel, const bool inIsBInput)
ULWord registerValue
My register value to use in a ReadRegister or WriteRegister call.
NTV2DeviceID
Identifies a specific AJA NTV2 device model number. The NTV2DeviceID is actually the PROM part number...
Definition: ntv2enums.h:20
ULWord registerNumber
My register number to use in a ReadRegister or WriteRegister call.
bool NTV2DeviceCanDoWidget(const NTV2DeviceID inDeviceID, const NTV2WidgetID inWidgetID)
Invalid or "not found".
Definition: ntv2enums.h:98
#define NTV2_INPUT_SOURCE_IS_HDMI(_inpSrc_)
Definition: ntv2enums.h:1281
NTV2InputXptID GetLUTInputXptFromChannel(const NTV2Channel inLUT)
static bool GetAllRoutingRegInfos(const NTV2InputXptIDSet &inInputs, NTV2RegisterWrites &outRegInfos)
Returns all routing registers for the given set of input crosspoints.
NTV2XptConnections mChanged
Optional, to show changed connections.
std::set< NTV2WidgetID > NTV2WidgetIDSet
A collection of distinct NTV2WidgetID values.
virtual NTV2OutputXptID GetConnectedOutput(const NTV2InputXptID inSignalInput) const
bool mUseRouter
If true, use calls to CNTV2SignalRouter instead of CNTV2Card.
std::string mPostClassText
Class postfix text.
void split(const std::string &str, const char delim, std::vector< std::string > &elems)
Definition: common.cpp:350
static NTV2StringList & Tokenize(const string &inString, NTV2StringList &outTokens, const string &inDelimiters=" ", bool inTrimEmpty=false)
NTV2InputXptID GetMixerBGInputXpt(const NTV2Channel inChannel, const bool inIsKey)
std::vector< std::string > NTV2StringList
Definition: ntv2utils.h:1155
std::string mPreFunctionText
Function name prefix text.
NTV2OutputXptID GetTSIMuxOutputXptFromChannel(const NTV2Channel inChannel, const bool inLinkB, const bool inIsRGB)
NTV2RegWrites NTV2RegisterReads
NTV2OutputXptID GetInputSourceOutputXpt(const NTV2InputSource inInputSource, const bool inIsSDI_DS2, const bool inIsHDMI_RGB, const UWord inHDMI_Quadrant)
ULWord registerShift
My register shift value to use in a ReadRegister or WriteRegister call.
virtual bool HasInput(const NTV2InputXptID inSignalInput) const
Answers true if I contain a connection that involves the given input (signal sink).
static bool IsRGBOnlyInputXpt(const NTV2InputXptID inInputXpt)
static NTV2InputXptID StringToNTV2InputCrosspointID(const std::string &inStr)
Returns a string containing the most compact human-readable form for a given input crosspoint...
std::pair< NTV2InputXptID, NTV2OutputXptID > NTV2SignalConnection
NTV2XptConnections connections
Definition: ntv2vcam.cpp:1011
std::string mPreXptText
Crosspoint variable prefix text.
#define SRiDBG(__x__)
static const ULWord sSignalRouterRegMasks[]
static bool GetCrosspointSelectGroupRegisterInfo(const NTV2InputCrosspointID inInputXpt, uint32_t &outXptRegNum, uint32_t &outMaskIndex)
Answers with the crosspoint select register and mask information for a given widget input...
static bool ToCodeString(std::string &outCode, const NTV2XptConnections &inConnections, const PrintCodeConfig &inConfig=PrintCodeConfig())
Converts the given map of crosspoint connections into source code.
NTV2InputXptID GetCSCInputXptFromChannel(const NTV2Channel inChannel, const bool inIsKeyInput)
std::string mPostXptText
Crosspoint variable postfix text.
Declares NTV2DeviceCanDo... and NTV2DeviceGetNum... functions. This module is included at compile tim...
static bool Is3GSDIWidgetType(const NTV2WidgetType inWidgetType)
NTV2RoutingEntry & operator=(const NTV2RegInfo &inRHS)
Assigns an NTV2RegInfo to me.
NTV2InputXptID GetDLInInputXptFromChannel(const NTV2Channel inChannel, const bool inLinkB)
static NTV2WidgetID WidgetIDFromTypeAndChannel(const NTV2WidgetType inWidgetType, const NTV2Channel inChannel)
#define NTV2_OUTPUT_DEST_IS_ANALOG(_dest_)
Definition: ntv2enums.h:1345
#define NTV2_OUTPUT_DEST_IS_SDI(_dest_)
Definition: ntv2enums.h:1346
#define NTV2_IS_VALID_CHANNEL(__x__)
Definition: ntv2enums.h:1371
static bool GetAllWidgetInputs(const NTV2DeviceID inDeviceID, NTV2InputXptIDSet &outInputs)
Returns all supported widget input crosspoints for the given device.
static bool IsDualLinkInWidgetType(const NTV2WidgetType inWidgetType)
NTV2InputSource
Identifies a specific video input source.
Definition: ntv2enums.h:1262
virtual bool PrintCode(std::string &outCode, const PrintCodeConfig &inConfig=PrintCodeConfig()) const
Prints me as source code to the given output stream.
Originally 0x01. Changed to 0x00 in SDK 17.1.
Definition: ntv2enums.h:2754
static bool DisposeInstance(void)
std::string mPostVariableText
Variable postfix text.
std::string & strip(std::string &str, const std::string &ws)
Definition: common.cpp:461
NTV2WidgetIDSet::const_iterator NTV2WidgetIDSetConstIter
An iterator for iterating over a read-only NTV2WidgetIDSet.
std::string mPreVariableText
Variable prefix text.
static bool GetWidgetForOutput(const NTV2OutputXptID inOutputXpt, NTV2WidgetID &outWidgetID, const NTV2DeviceID inDeviceID=DEVICE_ID_NOTFOUND)
Returns the widget that "owns" the specified output crosspoint.
#define DEC(__x__)
static bool GetWidgetForInput(const NTV2InputXptID inInputXpt, NTV2WidgetID &outWidgetID, const NTV2DeviceID inDeviceID=DEVICE_ID_NOTFOUND)
Returns the widget that "owns" the specified input crosspoint.
Declares numerous NTV2 utility functions.
virtual std::ostream & Print(std::ostream &inOutStream, const bool inForRetailDisplay=false) const
Prints me in a human-readable format to the given output stream.
std::set< NTV2InputXptID > NTV2InputXptIDSet
A collection of distinct NTV2InputXptID values.
std::string mPreCommentText
Comment prefix text.
virtual bool RemoveConnection(const NTV2InputXptID inSignalInput, const NTV2OutputXptID inSignalOutput)
Removes the connection between the specified input (signal sink) and output (signal source)...
NTV2InputXptID GetTSIMuxInputXptFromChannel(const NTV2Channel inChannel, const bool inLinkB)
static AJALock gRoutingExpertLock
virtual bool Compare(const CNTV2SignalRouter &inRHS, NTV2XptConnections &outNew, NTV2XptConnections &outChanged, NTV2XptConnections &outMissing) const
Compares me with another routing, and returns three connection mappings as a result of the comparison...
static bool GetWidgetIDs(const NTV2DeviceID inDeviceID, NTV2WidgetIDSet &outWidgets)
Returns the widget IDs supported by the given device.
static bool IsDualLinkOutWidgetType(const NTV2WidgetType inWidgetType)
PrintCodeConfig()
Default constructor sets the following default settings:
virtual bool ResetFromRegisters(const NTV2InputXptIDSet &inInputXpts, const NTV2RegisterReads &inRegReads)
Resets me, erasing any/all existing connections, then rebuilding my connections from the given regist...
std::string mPreClassText
Class prefix text.
NTV2WidgetID
Definition: ntv2enums.h:2909
static bool MakeRouteROMRegisters(NTV2RegReads &outROMRegisters)
Prepares an initialized, zeroed NTV2RegReads that&#39;s prepared to read all ROM registers from a device...
bool NTV2DeviceCanDo8KVideo(const NTV2DeviceID inDeviceID)
uint16_t UWord
Definition: ajatypes.h:221
std::string mPostFunctionText
Function name postfix text.
NTV2OutputXptID GetFrameStoreOutputXptFromChannel(const NTV2Channel inChannel, const bool inIsRGB, const bool inIs425)
static RoutingExpertPtr GetInstance(const bool inCreateIfNecessary=true)
std::string mLineBreakText
Text to use for line breaks.
static bool GetWidgetsForOutput(const NTV2OutputXptID inOutputXpt, NTV2WidgetIDSet &outWidgetIDs)
Returns the widgets that "own" the specified output crosspoint.
#define NTV2_INPUT_SOURCE_IS_ANALOG(_inpSrc_)
Definition: ntv2enums.h:1282
bool mShowComments
If true, show comments in the generated code.
static bool IsDualLinkWidgetType(const NTV2WidgetType inWidgetType)
static bool IsSDIWidgetType(const NTV2WidgetType inWidgetType)
NTV2OutputXptID GetCSCOutputXptFromChannel(const NTV2Channel inChannel, const bool inIsKey, const bool inIsRGB)
std::pair< NTV2InputXptID, NTV2OutputXptID > NTV2XptConnection
enum NTV2InputCrosspointID NTV2InputXptID
NTV2InputXptID GetSDIOutputInputXpt(const NTV2Channel inChannel, const bool inIsDS2)
std::multimap< NTV2InputXptID, NTV2OutputXptID > NTV2PossibleConnections
A map of zero or more one-to-many possible NTV2InputXptID to NTV2OutputXptID connections.
static bool IsHDMIWidgetType(const NTV2WidgetType inWidgetType)
Private include file for all ajabase sources.
NTV2OutputXptID GetMixerOutputXptFromChannel(const NTV2Channel inChannel, const bool inIsKey)
NTV2XptConnections mMissing
Optional, to show deleted connections.
std::string NTV2OutputCrosspointIDToString(const NTV2OutputCrosspointID inValue, const bool inForRetailDisplay=false)
Definition: ntv2utils.cpp:5957
static bool GetWidgetsForInput(const NTV2InputXptID inInputXpt, NTV2WidgetIDSet &outWidgetIDs)
Returns the widgets that "own" the specified input crosspoint.
std::map< NTV2InputXptID, NTV2OutputXptID > NTV2XptConnections
virtual bool ResetFrom(const NTV2XptConnections &inConnections)
Resets me, replacing any/all existing connections with the given connections.
static std::string NTV2OutputCrosspointIDToString(const NTV2OutputXptID inOutputXpt)
Returns a string containing the most compact human-readable form for a given output crosspoint...
static bool IsYUVOnlyInputXpt(const NTV2InputXptID inInputXpt)
std::vector< NTV2RegInfo > NTV2RegisterWrites
static NTV2Channel WidgetIDToChannel(const NTV2WidgetID inWidgetID)
#define NTV2_INPUT_SOURCE_IS_SDI(_inpSrc_)
Definition: ntv2enums.h:1283
std::string & lower(std::string &str)
Definition: common.cpp:436
#define SRFAIL(__x__)
NTV2RegWrites NTV2RegReads
An ordered sequence of zero or more NTV2RegInfo structs intended for ReadRegister.
#define NTV2_IS_VALID_WIDGET(__w__)
Definition: ntv2enums.h:3045
#define SRWARN(__x__)
static NTV2WidgetType WidgetIDToType(const NTV2WidgetID inWidgetID)
static bool GetAllWidgetOutputs(const NTV2DeviceID inDeviceID, NTV2OutputXptIDSet &outOutputs)
Returns all supported widget output crosspoints for the given device.
std::string & replace(std::string &str, const std::string &from, const std::string &to)
Definition: common.cpp:110
NTV2OutputXptID GetSDIInputOutputXptFromChannel(const NTV2Channel inChannel, const bool inIsDS2)
static NTV2OutputXptID StringToNTV2OutputCrosspointID(const std::string &inStr)
Returns the output crosspoint that corresponds to the given string.
std::set< NTV2OutputXptID > NTV2OutputXptIDSet
A collection of distinct NTV2OutputXptID values.
static bool GetWidgetInputs(const NTV2WidgetID inWidgetID, NTV2InputXptIDSet &outInputs)
Returns the input crosspoints known to be "owned" by the given widget.
enum NTV2OutputCrosspointID NTV2OutputXptID
NTV2InputXptID GetOutputDestInputXpt(const NTV2OutputDestination inOutputDest, const bool inIsSDI_DS2, const UWord inHDMI_Quadrant)
NTV2StringList::const_iterator NTV2StringListConstIter
Definition: ntv2utils.h:1157
#define NTV2_WIDGET_FIRST
Identifies firmware widgets that logically can have zero or more signal inputs (identified by NTV2Inp...
Definition: ntv2enums.h:2908
Declares the CNTV2RegisterExpert class.
NTV2RegReadsConstIter FindFirstMatchingRegisterNumber(const uint32_t inRegNum, const NTV2RegReads &inRegInfos)
Returns a const iterator to the first entry in the NTV2RegInfo collection with a matching register nu...
static bool IsHDMIInWidgetType(const NTV2WidgetType inWidgetType)
static bool IsSDIInputWidgetType(const NTV2WidgetType inWidgetType)