1%pure-parser
2%no-lines
3%output "gen/parser.cpp"
4%defines "gen/parser.h"
5
6%code requires {
7/*
8 * This file is part of Wireless Display Software for Linux OS
9 *
10 * Copyright (C) 2015 Intel Corporation.
11 *
12 * This library is free software; you can redistribute it and/or
13 * modify it under the terms of the GNU Lesser General Public
14 * License as published by the Free Software Foundation; either
15 * version 2.1 of the License, or (at your option) any later version.
16 *
17 * This library is distributed in the hope that it will be useful,
18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
20 * Lesser General Public License for more details.
21 *
22 * You should have received a copy of the GNU Lesser General Public
23 * License along with this library; if not, write to the Free Software
24 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
25 * 02110-1301 USA
26 */
27
28   #include <map>
29   #include <memory>
30   #include "libwds/rtsp/audiocodecs.h"
31   #include "libwds/rtsp/contentprotection.h"
32   #include "libwds/rtsp/triggermethod.h"
33   #include "libwds/rtsp/route.h"
34   #include "libwds/rtsp/uibcsetting.h"
35   #include "libwds/rtsp/uibccapability.h"
36
37   #define YYLEX_PARAM scanner
38
39   namespace wds {
40      struct AudioCodec;
41   namespace rtsp {
42      class Driver;
43      class Scanner;
44      class Message;
45      class Header;
46      class TransportHeader;
47      class Property;
48      class PropertyErrors;
49      class Payload;
50      class VideoFormats;
51      struct H264Codec;
52      struct H264Codec3d;
53   }
54   }
55}
56
57%lex-param {void* scanner} { std::unique_ptr<wds::rtsp::Message>& message }
58%parse-param {void* scanner} { std::unique_ptr<wds::rtsp::Message>& message }
59
60%code {
61#include <iostream>
62#include <cstdlib>
63#include <string>
64#include <vector>
65#include <map>
66
67#include "libwds/rtsp/driver.h"
68#include "libwds/rtsp/message.h"
69#include "libwds/rtsp/header.h"
70#include "libwds/rtsp/transportheader.h"
71#include "libwds/rtsp/payload.h"
72#include "libwds/rtsp/reply.h"
73#include "libwds/rtsp/options.h"
74#include "libwds/rtsp/getparameter.h"
75#include "libwds/rtsp/setparameter.h"
76#include "libwds/rtsp/play.h"
77#include "libwds/rtsp/teardown.h"
78#include "libwds/rtsp/pause.h"
79#include "libwds/rtsp/setup.h"
80#include "libwds/rtsp/audiocodecs.h"
81#include "libwds/rtsp/videoformats.h"
82#include "libwds/rtsp/formats3d.h"
83#include "libwds/rtsp/contentprotection.h"
84#include "libwds/rtsp/displayedid.h"
85#include "libwds/rtsp/coupledsink.h"
86#include "libwds/rtsp/triggermethod.h"
87#include "libwds/rtsp/clientrtpports.h"
88#include "libwds/rtsp/i2c.h"
89#include "libwds/rtsp/avformatchangetiming.h"
90#include "libwds/rtsp/standbyresumecapability.h"
91#include "libwds/rtsp/standby.h"
92#include "libwds/rtsp/idrrequest.h"
93#include "libwds/rtsp/connectortype.h"
94#include "libwds/rtsp/preferreddisplaymode.h"
95#include "libwds/rtsp/presentationurl.h"
96#include "libwds/rtsp/uibccapability.h"
97
98#define UNUSED_TOKEN(T) (void)T
99#define DELETE_TOKEN(T) \
100    delete T;           \
101    T = nullptr
102}
103
104%union {
105   std::string* sval;
106   unsigned long long int nval;
107   bool bool_val;
108   std::vector<std::string>* vsval;
109   wds::rtsp::Message* message;
110   wds::rtsp::Header* header;
111   wds::rtsp::Payload* mpayload;
112   wds::AudioFormats audio_format;
113   wds::rtsp::Property* property;
114   std::vector<unsigned short>* error_list;
115   wds::rtsp::PropertyErrors* property_errors;
116   std::map<wds::rtsp::PropertyType, std::shared_ptr<wds::rtsp::PropertyErrors>>* property_error_map;
117   std::vector<wds::rtsp::H264Codec>* codecs;
118   wds::rtsp::H264Codec* codec;
119   std::vector<wds::rtsp::H264Codec3d>* codecs_3d;
120   wds::rtsp::H264Codec3d* codec_3d;
121   wds::rtsp::ContentProtection::HDCPSpec hdcp_spec;
122   wds::rtsp::TriggerMethod::Method trigger_method;
123   wds::rtsp::Route::Destination route_destination;
124   bool uibc_setting;
125   std::vector<wds::rtsp::UIBCCapability::InputCategory>* input_category_list;
126   std::vector<wds::rtsp::UIBCCapability::InputType>* generic_cap_list;
127   std::vector<wds::rtsp::UIBCCapability::DetailedCapability>* hidc_cap_list;
128   wds::rtsp::UIBCCapability::InputCategory input_category_list_value;
129   wds::rtsp::UIBCCapability::InputType generic_cap_list_value;
130   wds::rtsp::UIBCCapability::DetailedCapability* hidc_cap_list_value;
131   wds::rtsp::UIBCCapability::InputPath input_path;
132   wds::rtsp::Method method;
133   std::vector<wds::rtsp::Method>* methods;
134   wds::rtsp::PropertyType parameter;
135   std::vector<wds::rtsp::PropertyType>* parameters;
136   std::vector<wds::AudioCodec>* audio_codecs;
137   wds::AudioCodec* audio_codec;
138   std::pair<std::string, unsigned int>* session_info;
139   wds::rtsp::TransportHeader* transport;
140}
141
142%token END 0
143%token WFD_SP
144%token <nval> WFD_NUM
145%token WFD_OPTIONS
146%token WFD_SET_PARAMETER
147%token WFD_GET_PARAMETER
148%token WFD_SETUP
149%token WFD_PLAY
150%token WFD_TEARDOWN
151%token WFD_PAUSE
152%token WFD_END
153%token WFD_RESPONSE
154%token <nval> WFD_RESPONSE_CODE
155%token <sval> WFD_STRING
156%token <sval> WFD_GENERIC_PROPERTY
157%token <sval> WFD_HEADER
158%token WFD_CSEQ
159%token WFD_RESPONSE_METHODS
160%token WFD_TAG
161%token WFD_SUPPORT_CHECK
162%token <sval> WFD_REQUEST_URI
163%token WFD_CONTENT_TYPE
164%token <sval> WFD_MIME
165%token WFD_CONTENT_LENGTH
166%token WFD_AUDIO_CODECS
167%token WFD_VIDEO_FORMATS
168%token WFD_3D_FORMATS
169%token WFD_CONTENT_PROTECTION
170%token WFD_DISPLAY_EDID
171%token WFD_COUPLED_SINK
172%token WFD_TRIGGER_METHOD
173%token WFD_PRESENTATION_URL
174%token WFD_CLIENT_RTP_PORTS
175%token WFD_ROUTE
176%token WFD_I2C
177%token WFD_AV_FORMAT_CHANGE_TIMING
178%token WFD_PREFERRED_DISPLAY_MODE
179%token WFD_UIBC_CAPABILITY
180%token WFD_UIBC_SETTING
181%token WFD_STANDBY_RESUME_CAPABILITY
182%token WFD_STANDBY_IN_REQUEST
183%token WFD_STANDBY_IN_RESPONSE
184%token WFD_CONNECTOR_TYPE
185%token WFD_IDR_REQUEST
186%token WFD_AUDIO_CODECS_ERROR
187%token WFD_VIDEO_FORMATS_ERROR
188%token WFD_3D_FORMATS_ERROR
189%token WFD_CONTENT_PROTECTION_ERROR
190%token WFD_DISPLAY_EDID_ERROR
191%token WFD_COUPLED_SINK_ERROR
192%token WFD_TRIGGER_METHOD_ERROR
193%token WFD_PRESENTATION_URL_ERROR
194%token WFD_CLIENT_RTP_PORTS_ERROR
195%token WFD_ROUTE_ERROR
196%token WFD_I2C_ERROR
197%token WFD_AV_FORMAT_CHANGE_TIMING_ERROR
198%token WFD_PREFERRED_DISPLAY_MODE_ERROR
199%token WFD_UIBC_CAPABILITY_ERROR
200%token WFD_UIBC_SETTING_ERROR
201%token WFD_STANDBY_RESUME_CAPABILITY_ERROR
202%token WFD_STANDBY_ERROR
203%token WFD_CONNECTOR_TYPE_ERROR
204%token WFD_IDR_REQUEST_ERROR
205%token <sval> WFD_GENERIC_PROPERTY_ERROR
206%token WFD_NONE
207%token WFD_AUDIO_CODEC_LPCM
208%token WFD_AUDIO_CODEC_AAC
209%token WFD_AUDIO_CODEC_AC3
210%token WFD_HDCP_SPEC_2_0
211%token WFD_HDCP_SPEC_2_1
212%token <nval> WFD_IP_PORT
213%token <sval> WFD_PRESENTATION_URL_0
214%token <sval> WFD_PRESENTATION_URL_1
215%token WFD_STREAM_PROFILE
216%token WFD_MODE_PLAY
217%token WFD_ROUTE_PRIMARY
218%token WFD_ROUTE_SECONDARY
219%token WFD_INPUT_CATEGORY_LIST
220%token WFD_INPUT_CATEGORY_GENERIC
221%token WFD_INPUT_CATEGORY_HIDC
222%token WFD_GENERIC_CAP_LIST
223%token WFD_INPUT_TYPE_KEYBOARD
224%token WFD_INPUT_TYPE_MOUSE
225%token WFD_INPUT_TYPE_SINGLE_TOUCH
226%token WFD_INPUT_TYPE_MULTI_TOUCH
227%token WFD_INPUT_TYPE_JOYSTICK
228%token WFD_INPUT_TYPE_CAMERA
229%token WFD_INPUT_TYPE_GESTURE
230%token WFD_INPUT_TYPE_REMOTE_CONTROL
231%token WFD_HIDC_CAP_LIST
232%token WFD_INPUT_PATH_INFRARED
233%token WFD_INPUT_PATH_USB
234%token WFD_INPUT_PATH_BT
235%token WFD_INPUT_PATH_WIFI
236%token WFD_INPUT_PATH_ZIGBEE
237%token WFD_INPUT_PATH_NOSP
238%token WFD_UIBC_SETTING_ENABLE
239%token WFD_UIBC_SETTING_DISABLE
240%token WFD_SUPPORTED
241%token WFD_SESSION
242%token <sval> WFD_SESSION_ID
243%token WFD_TIMEOUT
244%token WFD_TRANSPORT
245%token WFD_SERVER_PORT
246
247%type <message> options set_parameter get_parameter setup play teardown pause
248%type <message> wfd_reply command
249%type <header> headers
250
251%type <sval> wfd_content_type
252%type <session_info> wfd_session
253%type <method> wfd_method
254%type <methods> wfd_methods wfd_supported_methods
255%type <nval> wfd_content_length
256%type <nval> wfd_cseq
257%type <audio_format> wfd_audio_codec_type
258%type <property> wfd_property wfd_property_audio_codecs
259%type <property> wfd_property_video_formats
260%type <property> wfd_property_3d_formats
261%type <property> wfd_content_protection
262%type <property> wfd_display_edid
263%type <property> wfd_coupled_sink
264%type <property> wfd_trigger_method
265%type <property> wfd_presentation_url
266%type <property> wfd_client_rtp_ports
267%type <property> wfd_route
268%type <property> wfd_I2C
269%type <property> wfd_av_format_change_timing
270%type <property> wfd_preferred_display_mode
271%type <property> wfd_uibc_capability
272%type <property> wfd_uibc_setting
273%type <property> wfd_standby_resume_capability
274%type <property> wfd_connector_type
275%type <mpayload> wdf_property_map
276%type <mpayload> wfd_property_error_map
277%type <property_errors> wfd_property_errors
278%type <error_list> wfd_error_list
279%type <mpayload> payload
280%type <codecs> wfd_h264_codecs
281%type <codec> wfd_h264_codec
282%type <nval> wfd_max_hres
283%type <nval> wfd_max_vres
284%type <codecs_3d> wfd_h264_codecs_3d
285%type <codec_3d> wfd_h264_codec_3d
286%type <hdcp_spec> hdcp2_spec
287%type <sval> wfd_edid_payload
288%type <nval> wfd_sink_address
289%type <trigger_method> wfd_supported_trigger_methods
290%type <route_destination> wfd_route_destination
291%type <nval> wfd_port
292%type <uibc_setting> wfd_uibc_setting_value
293%type <bool_val> wfd_standby_resume_capability_value
294%type <sval> wfd_presentation_url0 wfd_presentation_url1
295%type <input_category_list> wfd_input_category_list wfd_input_category_list_values
296%type <generic_cap_list> wfd_generic_cap_list wfd_generic_cap_list_values
297%type <hidc_cap_list> wfd_hidc_cap_list wfd_hidc_cap_list_values
298%type <input_category_list_value> wfd_input_category_list_value
299%type <generic_cap_list_value> wfd_generic_cap_list_value
300%type <hidc_cap_list_value> wfd_hidc_cap_list_value
301%type <input_path> wfd_input_path
302%type <parameter> wfd_parameter
303%type <mpayload> wfd_parameter_list
304%type <audio_codecs> wfd_audio_codec_list
305%type <audio_codec> wfd_audio_codec
306%type <transport> wfd_transport
307
308%destructor { DELETE_TOKEN($$); } WFD_STRING WFD_REQUEST_URI WFD_MIME WFD_GENERIC_PROPERTY
309%destructor { DELETE_TOKEN($$); } wfd_methods wfd_supported_methods
310%destructor { DELETE_TOKEN($$); } wfd_h264_codec wfd_h264_codecs
311%destructor { DELETE_TOKEN($$); } wfd_h264_codec_3d wfd_h264_codecs_3d
312%destructor { DELETE_TOKEN($$); } wfd_edid_payload
313%destructor { DELETE_TOKEN($$); } wfd_hidc_cap_list_value
314%destructor { DELETE_TOKEN($$); } wfd_parameter_list
315%destructor { DELETE_TOKEN($$); } wfd_audio_codec wfd_audio_codec_list
316
317%%
318
319start: message
320  ;
321
322message:
323    command headers {
324      message.reset($1);
325      $1->set_header(std::unique_ptr<wds::rtsp::Header>($2));
326    }
327  | payload {
328      if (message && $1)
329        message->set_payload(std::unique_ptr<wds::rtsp::Payload>($1));
330      else
331        YYERROR;
332    }
333  | error {
334      message.reset();
335      std::cerr << "Unknown message" << std::endl;
336      YYABORT;
337    }
338  ;
339
340command:
341    options
342  | set_parameter
343  | get_parameter
344  | setup
345  | play
346  | teardown
347  | pause
348  | wfd_reply
349  ;
350
351options:
352    WFD_OPTIONS WFD_SP '*' WFD_SP WFD_END {
353      $$ = new wds::rtsp::Options("*");
354    }
355  | WFD_OPTIONS WFD_SP WFD_REQUEST_URI WFD_SP WFD_END {
356      $$ = new wds::rtsp::Options(*$3);
357      DELETE_TOKEN($3);
358    }
359  ;
360
361set_parameter:
362    WFD_SET_PARAMETER WFD_SP WFD_REQUEST_URI WFD_SP WFD_END {
363      $$ = new wds::rtsp::SetParameter(*$3);
364      DELETE_TOKEN($3);
365    }
366  ;
367
368get_parameter:
369    WFD_GET_PARAMETER WFD_SP WFD_REQUEST_URI WFD_SP WFD_END {
370      $$ = new wds::rtsp::GetParameter(*$3);
371      DELETE_TOKEN($3);
372    }
373  ;
374
375setup:
376    WFD_SETUP WFD_SP WFD_REQUEST_URI WFD_SP WFD_END {
377      $$ = new wds::rtsp::Setup(*$3);
378      DELETE_TOKEN($3);
379    }
380  ;
381
382play:
383    WFD_PLAY WFD_SP WFD_REQUEST_URI WFD_SP WFD_END {
384      $$ = new wds::rtsp::Play(*$3);
385      DELETE_TOKEN($3);
386    }
387  ;
388
389teardown:
390    WFD_TEARDOWN WFD_SP WFD_REQUEST_URI WFD_SP WFD_END {
391      $$ = new wds::rtsp::Teardown(*$3);
392      DELETE_TOKEN($3);
393    }
394  ;
395
396pause:
397    WFD_PAUSE WFD_SP WFD_REQUEST_URI WFD_SP WFD_END {
398      $$ = new wds::rtsp::Pause(*$3);
399      DELETE_TOKEN($3);
400    }
401  ;
402
403wfd_reply:
404    WFD_RESPONSE WFD_RESPONSE_CODE WFD_STRING {
405      DELETE_TOKEN($3);
406      $$ = new wds::rtsp::Reply($2);
407    }
408  ;
409
410headers:
411    {
412      $$ = new wds::rtsp::Header();
413    }
414  | headers wfd_cseq { $1->set_cseq($2); }
415  | headers WFD_SUPPORT_CHECK { $1->set_require_wfd_support(true); }
416  | headers wfd_content_type {
417          $1->set_content_type(*$2);
418          DELETE_TOKEN($2);
419      }
420  | headers wfd_content_length { $1->set_content_length($2); }
421  | headers wfd_supported_methods {
422          $1->set_supported_methods(*$2);
423          DELETE_TOKEN($2);
424      }
425  | headers wfd_session {
426      $1->set_session((*$2).first);
427      $1->set_timeout((*$2).second);
428      DELETE_TOKEN($2);
429    }
430  | headers wfd_transport { $1->set_transport ($2); }
431  | headers WFD_HEADER wfd_ows WFD_STRING {
432          $1->add_generic_header(*$2, *$4);
433          DELETE_TOKEN($2);
434          DELETE_TOKEN($4);
435      }
436  ;
437
438wfd_cseq:
439    WFD_CSEQ wfd_ows WFD_NUM {
440      $$ = $3;
441    }
442  ;
443
444wfd_content_type:
445    WFD_CONTENT_TYPE wfd_ows WFD_MIME {
446      $$ = $3;
447    }
448  ;
449
450wfd_content_length:
451    WFD_CONTENT_LENGTH wfd_ows WFD_NUM {
452      $$ = $3;
453    }
454  ;
455
456wfd_session:
457    WFD_SESSION WFD_SP WFD_SESSION_ID {
458      $$ = new std::pair<std::string, unsigned int>(*$3, 0);
459      DELETE_TOKEN($3);
460    }
461  | WFD_SESSION WFD_SP WFD_SESSION_ID WFD_TIMEOUT WFD_NUM {
462      $$ = new std::pair<std::string, unsigned int>(*$3, $5);
463      DELETE_TOKEN($3);
464    }
465  ;
466
467wfd_transport:
468    WFD_TRANSPORT WFD_NUM {
469      $$ = new wds::rtsp::TransportHeader();
470      $$->set_client_port ($2);
471    }
472  | WFD_TRANSPORT WFD_NUM '-' WFD_NUM {
473      $$ = new wds::rtsp::TransportHeader();
474      $$->set_client_port ($2);
475      $$->set_client_supports_rtcp (true);
476    }
477  | WFD_TRANSPORT WFD_NUM WFD_SERVER_PORT WFD_NUM {
478      $$ = new wds::rtsp::TransportHeader();
479      $$->set_client_port ($2);
480      $$->set_server_port ($4);
481    }
482  | WFD_TRANSPORT WFD_NUM '-' WFD_NUM WFD_SERVER_PORT WFD_NUM {
483      $$ = new wds::rtsp::TransportHeader();
484      $$->set_client_port ($2);
485      $$->set_client_supports_rtcp (true);
486      $$->set_server_port ($6);
487    }
488  | WFD_TRANSPORT WFD_NUM WFD_SERVER_PORT WFD_NUM '-' WFD_NUM {
489      $$ = new wds::rtsp::TransportHeader();
490      $$->set_client_port ($2);
491      $$->set_server_port ($4);
492      $$->set_server_supports_rtcp (true);
493    }
494  | WFD_TRANSPORT WFD_NUM '-' WFD_NUM WFD_SERVER_PORT WFD_NUM '-' WFD_NUM {
495      $$ = new wds::rtsp::TransportHeader();
496      $$->set_client_port ($2);
497      $$->set_client_supports_rtcp (true);
498      $$->set_server_port ($6);
499      $$->set_server_supports_rtcp (true);
500    }
501  ;
502
503wfd_supported_methods:
504    WFD_RESPONSE_METHODS wfd_ows wfd_methods {
505     $$ = $3;
506    }
507  ;
508
509wfd_methods:
510    wfd_method {
511      $$ = new std::vector<wds::rtsp::Method>();
512      $$->push_back($1);
513    }
514  | wfd_methods wfd_ows ',' wfd_ows wfd_method {
515      UNUSED_TOKEN($$);
516      $1->push_back($5);
517    }
518  ;
519
520wfd_method:
521    WFD_OPTIONS { $$ = wds::rtsp::OPTIONS; }
522  | WFD_SET_PARAMETER { $$ = wds::rtsp::SET_PARAMETER; }
523  | WFD_GET_PARAMETER { $$ = wds::rtsp::GET_PARAMETER; }
524  | WFD_SETUP { $$ = wds::rtsp::SETUP; }
525  | WFD_PLAY { $$ = wds::rtsp::PLAY; }
526  | WFD_TEARDOWN { $$ = wds::rtsp::TEARDOWN; }
527  | WFD_PAUSE { $$ = wds::rtsp::PAUSE; }
528  | WFD_TAG { $$ = wds::rtsp::ORG_WFA_WFD_1_0; }
529  ;
530
531wfd_ows:
532    /*blank*/
533  | WFD_SP
534  ;
535
536payload: {
537    $$ = 0;
538    }
539  | wfd_parameter_list
540  | wdf_property_map
541  | wfd_property_error_map
542  ;
543
544  /* used for GET_PARAMETER method */
545wfd_parameter_list:
546    wfd_parameter_list wfd_parameter {
547      UNUSED_TOKEN($$);
548      if (auto payload = ToGetParameterPayload($1))
549        payload->AddRequestProperty($2);
550      else
551        YYERROR;
552    }
553  | wfd_parameter {
554      $$ = new wds::rtsp::GetParameterPayload();
555      wds::rtsp::ToGetParameterPayload($$)->AddRequestProperty($1);
556    }
557  | wfd_parameter_list WFD_GENERIC_PROPERTY {
558      UNUSED_TOKEN($$);
559      if (auto payload = ToGetParameterPayload($1))
560        payload->AddRequestProperty(*$2);
561      else
562        YYERROR;
563      DELETE_TOKEN($2);
564    }
565  | WFD_GENERIC_PROPERTY {
566      $$ = new wds::rtsp::GetParameterPayload();
567      wds::rtsp::ToGetParameterPayload($$)->AddRequestProperty(*$1);
568      DELETE_TOKEN($1);
569    }
570  ;
571
572wfd_parameter:
573    WFD_AUDIO_CODECS { $$ = wds::rtsp::AudioCodecsPropertyType; }
574  | WFD_VIDEO_FORMATS { $$ = wds::rtsp::VideoFormatsPropertyType; }
575  | WFD_3D_FORMATS { $$ = wds::rtsp::Video3DFormatsPropertyType; }
576  | WFD_CONTENT_PROTECTION { $$ = wds::rtsp::ContentProtectionPropertyType; }
577  | WFD_DISPLAY_EDID { $$ = wds::rtsp::DisplayEdidPropertyType; }
578  | WFD_COUPLED_SINK { $$ = wds::rtsp::CoupledSinkPropertyType; }
579  | WFD_TRIGGER_METHOD { $$ = wds::rtsp::TriggerMethodPropertyType; }
580  | WFD_PRESENTATION_URL { $$ = wds::rtsp::PresentationURLPropertyType; }
581  | WFD_CLIENT_RTP_PORTS { $$ = wds::rtsp::ClientRTPPortsPropertyType; }
582  | WFD_ROUTE { $$ = wds::rtsp::RoutePropertyType; }
583  | WFD_I2C { $$ = wds::rtsp::I2CPropertyType; }
584  | WFD_AV_FORMAT_CHANGE_TIMING { $$ = wds::rtsp::AVFormatChangeTimingPropertyType; }
585  | WFD_PREFERRED_DISPLAY_MODE { $$ = wds::rtsp::PreferredDisplayModePropertyType; }
586  | WFD_UIBC_CAPABILITY { $$ = wds::rtsp::UIBCCapabilityPropertyType; }
587  | WFD_UIBC_SETTING { $$ = wds::rtsp::UIBCSettingPropertyType; }
588  | WFD_STANDBY_RESUME_CAPABILITY { $$ = wds::rtsp::StandbyResumeCapabilityPropertyType; }
589  | WFD_STANDBY_IN_REQUEST { $$ = wds::rtsp::StandbyPropertyType; }
590  | WFD_CONNECTOR_TYPE { $$ = wds::rtsp::ConnectorTypePropertyType; }
591  ;
592
593wfd_error_list:
594    WFD_NUM {
595      $$ = new std::vector<unsigned short>();
596      $$->push_back($1);
597    }
598  | wfd_error_list ',' WFD_SP WFD_NUM {
599      $1->push_back($4);
600    }
601
602wfd_property_errors:
603    WFD_AUDIO_CODECS_ERROR ':' WFD_SP wfd_error_list {
604      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::AudioCodecsPropertyType, *$4);
605      DELETE_TOKEN($4);
606    }
607  | WFD_VIDEO_FORMATS_ERROR ':' WFD_SP wfd_error_list {
608      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::VideoFormatsPropertyType, *$4);
609      DELETE_TOKEN($4);
610    }
611  | WFD_3D_FORMATS_ERROR ':' WFD_SP wfd_error_list {
612      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::Video3DFormatsPropertyType, *$4);
613      DELETE_TOKEN($4);
614    }
615  | WFD_CONTENT_PROTECTION_ERROR ':' WFD_SP wfd_error_list {
616      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::ContentProtectionPropertyType, *$4);
617      DELETE_TOKEN($4);
618    }
619  | WFD_DISPLAY_EDID_ERROR ':' WFD_SP wfd_error_list {
620      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::DisplayEdidPropertyType, *$4);
621      DELETE_TOKEN($4);
622    }
623  | WFD_COUPLED_SINK_ERROR ':' WFD_SP wfd_error_list {
624      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::CoupledSinkPropertyType, *$4);
625      DELETE_TOKEN($4);
626    }
627  | WFD_TRIGGER_METHOD_ERROR ':' WFD_SP wfd_error_list {
628      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::TriggerMethodPropertyType, *$4);
629      DELETE_TOKEN($4);
630    }
631  | WFD_PRESENTATION_URL_ERROR ':' WFD_SP wfd_error_list {
632      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::PresentationURLPropertyType, *$4);
633      DELETE_TOKEN($4);
634    }
635  | WFD_CLIENT_RTP_PORTS_ERROR ':' WFD_SP wfd_error_list {
636      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::ClientRTPPortsPropertyType, *$4);
637      DELETE_TOKEN($4);
638    }
639  | WFD_ROUTE_ERROR ':' WFD_SP wfd_error_list {
640      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::RoutePropertyType, *$4);
641      DELETE_TOKEN($4);
642    }
643  | WFD_I2C_ERROR ':' WFD_SP wfd_error_list {
644      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::I2CPropertyType, *$4);
645      DELETE_TOKEN($4);
646    }
647  | WFD_AV_FORMAT_CHANGE_TIMING_ERROR ':' WFD_SP wfd_error_list {
648      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::AVFormatChangeTimingPropertyType, *$4);
649      DELETE_TOKEN($4);
650    }
651  | WFD_PREFERRED_DISPLAY_MODE_ERROR ':' WFD_SP wfd_error_list {
652      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::PreferredDisplayModePropertyType, *$4);
653      DELETE_TOKEN($4);
654    }
655  | WFD_UIBC_CAPABILITY_ERROR ':' WFD_SP wfd_error_list {
656      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::UIBCCapabilityPropertyType, *$4);
657      DELETE_TOKEN($4);
658    }
659  | WFD_UIBC_SETTING_ERROR ':' WFD_SP wfd_error_list {
660      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::UIBCSettingPropertyType, *$4);
661      DELETE_TOKEN($4);
662    }
663  | WFD_STANDBY_RESUME_CAPABILITY_ERROR ':' WFD_SP wfd_error_list {
664      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::StandbyResumeCapabilityPropertyType, *$4);
665      DELETE_TOKEN($4);
666    }
667  | WFD_CONNECTOR_TYPE_ERROR ':' WFD_SP wfd_error_list {
668      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::ConnectorTypePropertyType, *$4);
669      DELETE_TOKEN($4);
670    }
671  | WFD_IDR_REQUEST_ERROR ':' WFD_SP wfd_error_list {
672      $$ = new wds::rtsp::PropertyErrors(wds::rtsp::IDRRequestPropertyType, *$4);
673      DELETE_TOKEN($4);
674    }
675  | WFD_GENERIC_PROPERTY_ERROR ':' WFD_SP wfd_error_list {
676      $$ = new wds::rtsp::PropertyErrors(*$1, *$4);
677      DELETE_TOKEN($1);
678      DELETE_TOKEN($4);
679    }
680  ;
681
682wfd_property_error_map:
683    wfd_property_errors {
684      $$ = new wds::rtsp::PropertyErrorPayload();
685      ToPropertyErrorPayload($$)->AddPropertyError(std::shared_ptr<wds::rtsp::PropertyErrors>($1));
686    }
687  | wfd_property_error_map wfd_property_errors {
688      if (auto payload = ToPropertyErrorPayload($1))
689        payload->AddPropertyError(std::shared_ptr<wds::rtsp::PropertyErrors>($2));
690      else
691        YYERROR;
692    }
693  ;
694
695wdf_property_map:
696    wfd_property {
697      $$ = new wds::rtsp::PropertyMapPayload();
698      ToPropertyMapPayload($$)->AddProperty(std::shared_ptr<wds::rtsp::Property>($1));
699    }
700  | wdf_property_map wfd_property {
701      if (auto payload = ToPropertyMapPayload($1))
702        payload->AddProperty(std::shared_ptr<wds::rtsp::Property>($2));
703      else
704        YYERROR;
705    }
706  ;
707
708wfd_property:
709    wfd_property_audio_codecs
710  | wfd_property_video_formats
711  | wfd_property_3d_formats
712  | wfd_content_protection
713  | wfd_display_edid
714  | wfd_coupled_sink
715  | wfd_trigger_method
716  | wfd_presentation_url
717  | wfd_client_rtp_ports
718  | wfd_route
719  | wfd_I2C
720  | wfd_av_format_change_timing
721  | wfd_preferred_display_mode
722  | wfd_uibc_capability
723  | wfd_uibc_setting
724  | wfd_standby_resume_capability
725  | wfd_connector_type
726  | WFD_STANDBY_IN_RESPONSE {
727      $$ = new wds::rtsp::Standby();
728    }
729  | WFD_IDR_REQUEST {
730      $$ = new wds::rtsp::IDRRequest();
731    }
732  | WFD_GENERIC_PROPERTY WFD_STRING {
733      $$ = new wds::rtsp::GenericProperty(*$1, *$2);
734      DELETE_TOKEN($1);
735      DELETE_TOKEN($2);
736    }
737  ;
738
739wfd_property_audio_codecs:
740    WFD_AUDIO_CODECS ':' WFD_SP wfd_audio_codec_list  {
741      $$ = new wds::rtsp::AudioCodecs(*$4);
742      DELETE_TOKEN($4);
743    }
744  | WFD_AUDIO_CODECS ':' WFD_SP WFD_NONE {
745      $$ = new wds::rtsp::AudioCodecs();
746    }
747  ;
748
749wfd_audio_codec_list:
750    wfd_audio_codec {
751      $$ = new std::vector<wds::AudioCodec>();
752      $$->push_back(*$1);
753      DELETE_TOKEN($1);
754    }
755  | wfd_audio_codec_list ',' WFD_SP wfd_audio_codec {
756      UNUSED_TOKEN($$);
757      $1->push_back(*$4);
758      DELETE_TOKEN($4);
759    }
760  ;
761
762wfd_audio_codec:
763  wfd_audio_codec_type WFD_SP WFD_NUM WFD_SP WFD_NUM {
764    $$ = new wds::AudioCodec($1, $3, $5);
765  }
766  ;
767
768wfd_audio_codec_type:
769    WFD_AUDIO_CODEC_LPCM { $$ = wds::LPCM; }
770  | WFD_AUDIO_CODEC_AAC { $$ = wds::AAC; }
771  | WFD_AUDIO_CODEC_AC3 { $$ = wds::AC3; }
772  ;
773
774wfd_property_video_formats:
775    WFD_VIDEO_FORMATS ':' wfd_ows WFD_NONE {
776      $$ = new wds::rtsp::VideoFormats();
777    }
778    /* native, preferred-display-mode-supported, H.264-codecs */
779  | WFD_VIDEO_FORMATS ':' wfd_ows WFD_NUM WFD_SP WFD_NUM WFD_SP wfd_h264_codecs {
780      $$ = new wds::rtsp::VideoFormats($4, $6, *$8);
781      DELETE_TOKEN($8);
782    }
783  ;
784
785wfd_h264_codecs:
786    wfd_h264_codec {
787      $$ = new wds::rtsp::H264Codecs();
788      $$->push_back(*$1);
789      DELETE_TOKEN($1);
790    }
791  | wfd_h264_codecs wfd_ows ',' wfd_ows wfd_h264_codec {
792      UNUSED_TOKEN($$);
793      $1->push_back(*$5);
794      DELETE_TOKEN($5);
795    }
796  ;
797
798wfd_h264_codec:
799    /* profile, level, misc-params , max-hres, max-vres */
800    WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP wfd_max_hres WFD_SP wfd_max_vres {
801      $$ = new wds::rtsp::H264Codec($1, $3, $5, $7, $9, $11, $13, $15, $17, $19, $21);
802    }
803
804
805wfd_h264_codecs_3d:
806    wfd_h264_codec_3d {
807      $$ = new wds::rtsp::H264Codecs3d();
808      $$->push_back(*$1);
809      DELETE_TOKEN($1);
810    }
811  | wfd_h264_codecs_3d wfd_ows ',' wfd_ows wfd_h264_codec_3d {
812      UNUSED_TOKEN($$);
813      $1->push_back(*$5);
814      DELETE_TOKEN($5);
815    }
816  ;
817
818wfd_h264_codec_3d:
819    WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP  wfd_max_hres WFD_SP wfd_max_vres {
820      $$ = new wds::rtsp::H264Codec3d($1, $3, $5, $7, $9, $11, $13, $15, $17);
821    }
822  ;
823
824wfd_max_hres:
825    WFD_NONE {
826      $$ = 0;
827    }
828  | WFD_NUM
829  ;
830
831wfd_max_vres:
832    WFD_NONE {
833      $$ = 0;
834    }
835  | WFD_NUM
836  ;
837
838wfd_property_3d_formats:
839    /* native, preferred-display-mode-supported, H.264-codecs */
840    WFD_3D_FORMATS ':' WFD_SP  WFD_NUM WFD_SP WFD_NUM WFD_SP wfd_h264_codecs_3d {
841      $$ = new wds::rtsp::Formats3d($4, $6, *$8);
842      DELETE_TOKEN($8);
843    }
844  | WFD_3D_FORMATS ':' WFD_SP WFD_NONE {
845      $$ = new wds::rtsp::Formats3d();
846    }
847  ;
848
849wfd_content_protection:
850    WFD_CONTENT_PROTECTION ':' WFD_SP WFD_NONE {
851      $$ = new wds::rtsp::ContentProtection();
852    }
853  | WFD_CONTENT_PROTECTION ':' WFD_SP hdcp2_spec WFD_SP WFD_IP_PORT WFD_NUM {
854      $$ = new wds::rtsp::ContentProtection($4, $7);
855    }
856  ;
857
858hdcp2_spec:
859    WFD_HDCP_SPEC_2_0 {
860      $$ = wds::rtsp::ContentProtection::HDCP_SPEC_2_0;
861    }
862  | WFD_HDCP_SPEC_2_1 {
863      $$ = wds::rtsp::ContentProtection::HDCP_SPEC_2_1;
864    }
865  ;
866
867wfd_display_edid:
868    WFD_DISPLAY_EDID ':' WFD_SP WFD_NONE {
869      $$ = new wds::rtsp::DisplayEdid();
870    }
871  | WFD_DISPLAY_EDID ':' WFD_SP WFD_NUM WFD_SP wfd_edid_payload {
872      $$ = new wds::rtsp::DisplayEdid($4, $6 ? *$6 : "");
873      DELETE_TOKEN($6);
874    }
875  ;
876
877wfd_edid_payload:
878    WFD_NONE {
879      $$ = 0;
880    }
881  | WFD_STRING
882  ;
883
884wfd_coupled_sink:
885    WFD_COUPLED_SINK ':' WFD_SP WFD_NONE {
886      $$ = new wds::rtsp::CoupledSink();
887    }
888  | WFD_COUPLED_SINK ':' WFD_SP WFD_NUM WFD_SP wfd_sink_address {
889      $$ = new wds::rtsp::CoupledSink($4, $6);
890    }
891  ;
892
893wfd_sink_address:
894    WFD_NONE {
895     $$ = -1;
896    }
897  | WFD_NUM
898  ;
899
900wfd_trigger_method:
901    WFD_TRIGGER_METHOD ':' WFD_SP wfd_supported_trigger_methods {
902      $$ = new wds::rtsp::TriggerMethod($4);
903    }
904  ;
905
906wfd_supported_trigger_methods:
907    WFD_SETUP {
908      $$ = wds::rtsp::TriggerMethod::SETUP;
909    }
910  | WFD_PAUSE{
911      $$ = wds::rtsp::TriggerMethod::PAUSE;
912    }
913  | WFD_TEARDOWN {
914      $$ = wds::rtsp::TriggerMethod::TEARDOWN;
915    }
916  | WFD_PLAY {
917      $$ = wds::rtsp::TriggerMethod::PLAY;
918    }
919  ;
920
921wfd_presentation_url:
922    WFD_PRESENTATION_URL ':' WFD_SP wfd_presentation_url0 WFD_SP wfd_presentation_url1 {
923      $$ = new wds::rtsp::PresentationUrl($4 ? *$4 : "", $6 ? *$6 : "");
924      DELETE_TOKEN($4);
925      DELETE_TOKEN($6);
926    }
927  ;
928
929wfd_presentation_url0:
930    WFD_NONE {
931      $$ = 0;
932    }
933  | WFD_PRESENTATION_URL_0
934  ;
935
936wfd_presentation_url1:
937    WFD_NONE {
938      $$ = 0;
939    }
940  | WFD_PRESENTATION_URL_1
941  ;
942
943wfd_client_rtp_ports:
944    WFD_CLIENT_RTP_PORTS ':' WFD_SP WFD_STREAM_PROFILE WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_MODE_PLAY {
945      $$ = new wds::rtsp::ClientRtpPorts($6, $8);
946  }
947
948wfd_route:
949    WFD_ROUTE ':' WFD_SP wfd_route_destination {
950      $$ = new wds::rtsp::Route($4);
951    }
952  ;
953
954wfd_route_destination:
955    WFD_ROUTE_PRIMARY {
956      $$ = wds::rtsp::Route::PRIMARY;
957    }
958  | WFD_ROUTE_SECONDARY {
959      $$ = wds::rtsp::Route::SECONDARY;
960    }
961  ;
962
963wfd_I2C:
964    WFD_I2C ':' WFD_SP wfd_port {
965      $$ = new wds::rtsp::I2C($4);
966    }
967  ;
968
969wfd_port:
970    WFD_NONE {
971      $$ = -1;
972    }
973  | WFD_NUM
974  ;
975
976wfd_av_format_change_timing:
977    WFD_AV_FORMAT_CHANGE_TIMING ':' WFD_SP WFD_NUM WFD_SP WFD_NUM {
978      $$ = new wds::rtsp::AVFormatChangeTiming($4, $6);
979    }
980  ;
981
982wfd_preferred_display_mode:
983    /* p-clock SP H SP HB SP HSPOL-HSOFF SP HSW SP V SP VB SP VSPOL-VSOFF SP VSW SP VBS3D SP 2d-s3d-modes SP p-depth SP H.264-codec */
984    WFD_PREFERRED_DISPLAY_MODE ':' WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP WFD_NUM WFD_SP wfd_h264_codec {
985      $$ = new wds::rtsp::PreferredDisplayMode($4, $6, $8, $10, $12, $14, $16, $18, $20, $22, $24, $26, *$28);
986      DELETE_TOKEN($28);
987    }
988  ;
989
990wfd_uibc_capability:
991    WFD_UIBC_CAPABILITY ':' WFD_SP WFD_NONE {
992      $$ = new wds::rtsp::UIBCCapability();
993    }
994  | WFD_UIBC_CAPABILITY ':' WFD_SP wfd_input_category_list ';' wfd_generic_cap_list ';' wfd_hidc_cap_list ';' WFD_IP_PORT wfd_port {
995      $$ = new wds::rtsp::UIBCCapability(*$4, *$6, *$8, $11);
996      DELETE_TOKEN($4);
997      DELETE_TOKEN($6);
998      DELETE_TOKEN($8);
999    }
1000  ;
1001
1002wfd_input_category_list:
1003    WFD_INPUT_CATEGORY_LIST wfd_input_category_list_values {
1004      $$ = $2;
1005    }
1006  ;
1007
1008wfd_input_category_list_values:
1009    WFD_NONE {
1010      $$ = new std::vector<wds::rtsp::UIBCCapability::InputCategory>();
1011    }
1012  | wfd_input_category_list_value {
1013      $$ = new std::vector<wds::rtsp::UIBCCapability::InputCategory>();
1014      $$->push_back($1);
1015    }
1016  | wfd_input_category_list_values ',' WFD_SP wfd_input_category_list_value {
1017      $1->push_back($4);
1018    }
1019  ;
1020
1021wfd_input_category_list_value:
1022    WFD_INPUT_CATEGORY_GENERIC {
1023      $$ = wds::rtsp::UIBCCapability::GENERIC;
1024    }
1025  | WFD_INPUT_CATEGORY_HIDC {
1026      $$ = wds::rtsp::UIBCCapability::HIDC;
1027    }
1028  ;
1029
1030wfd_generic_cap_list:
1031    WFD_GENERIC_CAP_LIST wfd_generic_cap_list_values {
1032      $$ = $2;
1033    }
1034  ;
1035
1036wfd_generic_cap_list_values:
1037    WFD_NONE {
1038      $$ = new std::vector<wds::rtsp::UIBCCapability::InputType>();
1039    }
1040  | wfd_generic_cap_list_value {
1041      $$ = new std::vector<wds::rtsp::UIBCCapability::InputType>();
1042      $$->push_back($1);
1043    }
1044  | wfd_generic_cap_list_values ',' WFD_SP wfd_generic_cap_list_value {
1045      $1->push_back($4);
1046    }
1047  ;
1048
1049wfd_generic_cap_list_value:
1050    WFD_INPUT_TYPE_KEYBOARD {
1051      $$ = wds::rtsp::UIBCCapability::KEYBOARD;
1052    }
1053  | WFD_INPUT_TYPE_MOUSE {
1054      $$ = wds::rtsp::UIBCCapability::MOUSE;
1055    }
1056  | WFD_INPUT_TYPE_SINGLE_TOUCH {
1057      $$ = wds::rtsp::UIBCCapability::SINGLE_TOUCH;
1058    }
1059  | WFD_INPUT_TYPE_MULTI_TOUCH {
1060      $$ = wds::rtsp::UIBCCapability::MULTI_TOUCH;
1061    }
1062  | WFD_INPUT_TYPE_JOYSTICK {
1063      $$ = wds::rtsp::UIBCCapability::JOYSTICK;
1064    }
1065  | WFD_INPUT_TYPE_CAMERA {
1066      $$ = wds::rtsp::UIBCCapability::CAMERA;
1067    }
1068  | WFD_INPUT_TYPE_GESTURE {
1069      $$ = wds::rtsp::UIBCCapability::GESTURE;
1070    }
1071  | WFD_INPUT_TYPE_REMOTE_CONTROL {
1072      $$ = wds::rtsp::UIBCCapability::REMOTE_CONTROL;
1073    }
1074  ;
1075
1076wfd_hidc_cap_list:
1077    WFD_HIDC_CAP_LIST wfd_hidc_cap_list_values {
1078      $$ = $2;
1079    }
1080  ;
1081
1082wfd_hidc_cap_list_values:
1083    WFD_NONE {
1084      $$ = new std::vector<wds::rtsp::UIBCCapability::DetailedCapability>();
1085    }
1086  | wfd_hidc_cap_list_value {
1087      $$ = new std::vector<wds::rtsp::UIBCCapability::DetailedCapability>();
1088      $$->push_back(*$1);
1089      DELETE_TOKEN($1);
1090    }
1091  | wfd_hidc_cap_list_values ',' WFD_SP wfd_hidc_cap_list_value {
1092      $1->push_back(*$4);
1093      DELETE_TOKEN($4);
1094    }
1095  ;
1096
1097wfd_hidc_cap_list_value:
1098    wfd_generic_cap_list_value '/' wfd_input_path {
1099      $$ = new wds::rtsp::UIBCCapability::DetailedCapability($1, $3);
1100    }
1101  ;
1102
1103
1104wfd_input_path:
1105    WFD_INPUT_PATH_INFRARED {
1106      $$ = wds::rtsp::UIBCCapability::INFRARED;
1107    }
1108  | WFD_INPUT_PATH_USB {
1109      $$ = wds::rtsp::UIBCCapability::USB;
1110    }
1111  | WFD_INPUT_PATH_BT {
1112      $$ = wds::rtsp::UIBCCapability::BT;
1113    }
1114  | WFD_INPUT_PATH_ZIGBEE {
1115      $$ = wds::rtsp::UIBCCapability::ZIGBEE;
1116    }
1117  | WFD_INPUT_PATH_WIFI {
1118      $$ = wds::rtsp::UIBCCapability::WI_FI;
1119    }
1120  | WFD_INPUT_PATH_NOSP {
1121      $$ = wds::rtsp::UIBCCapability::NO_SP;
1122    }
1123  ;
1124
1125wfd_uibc_setting:
1126    WFD_UIBC_SETTING ':' WFD_SP wfd_uibc_setting_value {
1127      $$ = new wds::rtsp::UIBCSetting($4);
1128    }
1129  ;
1130
1131wfd_uibc_setting_value:
1132    WFD_UIBC_SETTING_ENABLE {
1133      $$ = true;
1134    }
1135  | WFD_UIBC_SETTING_DISABLE {
1136      $$ = false;
1137    }
1138  ;
1139
1140wfd_standby_resume_capability:
1141    WFD_STANDBY_RESUME_CAPABILITY ':' WFD_SP wfd_standby_resume_capability_value {
1142      $$ = new wds::rtsp::StandbyResumeCapability($4);
1143    }
1144  ;
1145
1146wfd_standby_resume_capability_value:
1147    WFD_NONE {
1148      $$ = false;
1149    }
1150  | WFD_SUPPORTED {
1151      $$ = true;
1152    }
1153  ;
1154
1155wfd_connector_type:
1156    WFD_CONNECTOR_TYPE ':' WFD_SP WFD_NUM {
1157      $$ = new wds::rtsp::ConnectorType($4);
1158    }
1159  | WFD_CONNECTOR_TYPE ':' WFD_SP WFD_NONE {
1160      $$ = new wds::rtsp::ConnectorType();
1161    }
1162  ;
1163
1164%%
1165