public void StringGivenString() { ushort LangCodeEn = 0x656e; // "en" ushort LangCodeIs = 0x6973; // "is" ushort EncodingIdUtf8 = 106; ushort EncodingIdUtf16BE = 1013; ushort BaseA = 0x0100; ushort BaseB = 0x0100; // String str = "ambds\u2022nbdas\u00FEdlka\U00012004slkda"; ServiceElement element_ = new ServiceElement(ElementType.TextString, str); ServiceAttributeId id = ServiceRecord.CreateLanguageBasedAttributeId(UniversalAttributeId.ServiceName, (ServiceAttributeId)BaseA); ServiceAttribute attribute = new ServiceAttribute(id, element_); ServiceRecord record = CreateRecord(attribute); // LanguageBaseItem langBaseEn = new LanguageBaseItem(LangCodeEn, EncodingIdUtf8, BaseA); LanguageBaseItem langBaseIs = new LanguageBaseItem(LangCodeIs, EncodingIdUtf16BE, BaseB); Assert.AreEqual(str, record.GetMultiLanguageStringAttributeById( InTheHand.Net.Bluetooth.AttributeIds.UniversalAttributeId.ServiceName, langBaseEn)); Assert.AreEqual(str, record.GetMultiLanguageStringAttributeById( InTheHand.Net.Bluetooth.AttributeIds.UniversalAttributeId.ServiceName, langBaseIs)); // ServiceElement element = record.GetAttributeById(UniversalAttributeId.ServiceName, langBaseIs).Value; Assert.AreEqual(ElementTypeDescriptor.TextString, element.ElementTypeDescriptor); Assert.AreEqual(ElementType.TextString, element.ElementType); Assert.IsInstanceOfType(typeof(String), element.Value); Assert.AreEqual(str, element.GetValueAsStringUtf8()); Assert.AreEqual(str, element.GetValueAsString(Encoding.ASCII)); Assert.AreEqual(str, element.GetValueAsString(Encoding.Unicode)); }
/// <exclude/> protected virtual int CreateAttrId(ServiceAttributeId attrId, byte[] buf, int offset) { ServiceElement dummyElement = new ServiceElement( ElementType.UInt16, unchecked ((UInt16)attrId)); return(CreateElement(dummyElement, buf, offset)); }
/// <summary> /// Retrieves the name of the SDP Attribute ID with the given value in the /// specified Attribute ID class sets. /// </summary> /// - /// <remarks> /// Each particular service (ObexPushProfile, SerialPortProfile) etc defines /// its own SDP record content and the Attribute IDs are defined locally in /// each, and thus with values overlapping with other service specifications. /// Therefore for each profile we must define the set of Attribute IDs used, this /// is done by creating a class for each with the IDs defined as <c>const</c> /// member fields. /// </remarks> /// - /// <param name="id"> /// The Attribute Id as an <see cref="T:InTheHand.Net.Bluetooth.ServiceAttributeId"/> /// </param> /// <param name="attributeIdDefiningClasses"> /// The set of classes defining Attribute IDs for the service classed contained /// in the record containing this attribute id. /// </param> /// - /// <returns> /// A string containing the name of the Attribute ID whose numerical value is <paramref name="id"/>, /// or a null reference (<c>Nothing</c> in Visual Basic) if no such constant is found. /// </returns> public static string GetName(ServiceAttributeId id, Type[] attributeIdDefiningClasses) { string name = GetName(id, attributeIdDefiningClasses, new LanguageBaseItem[0], //HACK new LanguageBaseItem[0] -- instead of -- null out LanguageBaseItem applicableLangBase); return(name); }
/// <summary> /// Retrieves the name of the SDP Attribute ID with the given value in the /// specified Attribute ID class sets. /// </summary> /// - /// <remarks> /// Each particular service (ObexPushProfile, SerialPortProfile) etc defines /// its own SDP record content and the Attribute IDs are defined locally in /// each, and thus with values overlapping with other service specifications. /// Therefore for each profile we must define the set of Attribute IDs used, this /// is done by creating a class for each with the IDs defined as <c>const</c> /// member fields. /// </remarks> /// - /// <param name="id"> /// The Attribute Id as an <see cref="T:InTheHand.Net.Bluetooth.ServiceAttributeId"/> /// </param> /// <param name="attributeIdDefiningClasses"> /// The set of classes defining Attribute IDs for the service classed contained /// in the record containing this attribute id. /// </param> /// - /// <returns> /// A string containing the name of the Attribute ID whose numerical value is <paramref name="id"/>, /// or a null reference (<c>Nothing</c> in Visual Basic) if no such constant is found. /// </returns> public static string GetName(ServiceAttributeId id, Type[] attributeIdDefiningClasses) { LanguageBaseItem applicableLangBase; string name = GetName(id, attributeIdDefiningClasses, new LanguageBaseItem[0], //HACK new LanguageBaseItem[0] -- instead of -- null out applicableLangBase); return name; }
[CLSCompliant(false)] // internal use only public LanguageBaseItem(UInt16 naturalLanguage, UInt16 encodingId, ServiceAttributeId baseAttributeId) { if (baseAttributeId == 0) { throw new ArgumentOutOfRangeException("baseAttributeId"); } m_naturalLanguage = naturalLanguage; m_baseAttrId = baseAttributeId; m_encodingId = encodingId; }
//-------- protected sealed override int CreateAttrId(ServiceAttributeId attrId, byte[] buf, int offset) { this._attrId = attrId; this._isAttrId = true; int ret = base.CreateAttrId(attrId, buf, offset); this._isAttrId = false; return(ret); }
public static string GetName(ServiceAttributeId id, Type[] attributeIdDefiningClasses, LanguageBaseItem[] langBaseList, out LanguageBaseItem applicableLangBase) { if (attributeIdDefiningClasses == null) { throw new ArgumentNullException("attributeIdDefiningClasses"); } //HACK if (langBaseList == null) { if (langBaseList == null) { throw new ArgumentNullException("langBaseList"); } // Foreach: class that defines AttributeId enum. // Foreach: AttributeId enum field in that class. // Check whether its value matches the one being searched for, and return if so. // foreach (Type curDefiningType in attributeIdDefiningClasses) { //if (!(curDefiningType.IsSealed && curDefiningType.IsAbstract)) { } //---- System.Reflection.FieldInfo[] fieldArr = curDefiningType.GetFields( // With Public, no permissions required, apparently. System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static); foreach (System.Reflection.FieldInfo curField in fieldArr) { if (curField.FieldType == typeof(ServiceAttributeId)) { // A multi-language attribute or a just a normal one? Object[] dotnetAtttrs = curField.GetCustomAttributes(typeof(StringWithLanguageBaseAttribute), false); if (dotnetAtttrs.Length != 0) { System.Diagnostics.Debug.Assert(dotnetAtttrs.Length == 1, "Not that it's a problem for us at all, but that Attribute should only be applied once."); string name = _GetNameIfMatchesMultiLang(id, curField, langBaseList, out applicableLangBase); if (name != null) { return(name); } } else { // No just a normal Attribute, not language base offsetting. string name = _GetNameIfMatches(id, curField); if (name != null) { applicableLangBase = null; return(name); } } //else } } //foreach } //foreach // Not found. applicableLangBase = null; return(null); }
public String GetPrimaryMultiLanguageStringAttributeById(ServiceAttributeId id) { LanguageBaseItem lang = this.GetPrimaryLanguageBaseItem(); if (lang == null) { lang = LanguageBaseItem.CreateEnglishUtf8PrimaryLanguageItem(); } return(GetMultiLanguageStringAttributeById(id, lang)); }
//-------- protected override int CreateAttrId(ServiceAttributeId attrId, byte[] buf, int offset) { Debug.Assert(!this.needWrite, "overwrite"); this.attrId = attrId; this.isAttrId = true; int ret = base.CreateAttrId(attrId, buf, offset); this.isAttrId = false; return(ret); }
/// <overloads> /// Returns the attribute with the given ID. /// </overloads> /// - /// <summary> /// Returns the attribute with the given ID. /// </summary> /// - /// <param name="id">The Attribute Id as a <see cref="T:InTheHand.Net.Bluetooth.ServiceAttributeId"/>.</param> /// - /// <returns>A <see cref="T:InTheHand.Net.Bluetooth.ServiceAttribute"/> holding /// the attribute with the specified ID. /// Is never <see langword="null"/>. /// </returns> /// - /// <exception cref="T:System.Collections.Generic.KeyNotFoundException"> /// There is no attribute with the given Id in the record. /// Throws <see cref="T:System.ArgumentException"/> in NETCFv1 /// </exception> public ServiceAttribute GetAttributeById(ServiceAttributeId id) { bool found = TryGetAttributeById(id, out ServiceAttribute attribute); if (!found) { throw new KeyNotFoundException(ErrorMsgNoAttributeWithId); } System.Diagnostics.Debug.Assert(attribute != null); return(attribute); }
//-------------------------------------------------------------- /// <summary> /// Determines whether a TextString service attribute with the specified ID /// and natural language /// is in the List. /// </summary> /// - /// <param name="id">The id of the service attribute to locate, as a /// <see cref="T:InTheHand.Net.Bluetooth.ServiceAttributeId"/>.</param> /// <param name="language"> /// Which multi-language version of the string attribute to locate. /// </param> /// - /// <returns>true if item is found in the record; otherwise, false. </returns> public bool Contains(ServiceAttributeId id, LanguageBaseItem language) { if (language == null) { throw new ArgumentNullException("language"); } ServiceAttributeId actualId = CreateLanguageBasedAttributeId(id, language.AttributeIdBase); bool found = TryGetAttributeById(actualId, out var tmp); return(found && (tmp.Value.ElementType == ElementType.TextString)); }
private static void DoAreEqual(ExpectedServiceAttribute[] expectedAttributes, ServiceRecord record, int depth) { Assert.AreEqual(expectedAttributes.Length, record.Count, "Number of attributes."); for (int i = 0; i < expectedAttributes.Length; ++i) { ExpectedServiceAttribute expected = expectedAttributes[i]; ServiceAttribute row = record[i]; ServiceAttributeId expectedId = (ServiceAttributeId)expected.Id; Assert.AreEqual(expectedId, row.Id, "Attr Id."); DoAreEqual(expected, row.Value, depth + 1); }//for }
/// <summary> /// Returns the attribute with the given ID and natural language. /// </summary> /// - /// <param name="id">The id of the service attribute to locate, as a /// <see cref="T:InTheHand.Net.Bluetooth.ServiceAttributeId"/>.</param> /// <param name="language"> /// Which multi-language version of the string attribute to locate. /// </param> /// - /// <returns>A <see cref="T:InTheHand.Net.Bluetooth.ServiceAttribute"/> holding /// the attribute with the specified ID and language. /// Is never <see langword="null"/>. /// </returns> /// - /// <exception cref="T:System.Collections.Generic.KeyNotFoundException"> /// There is no attribute with the given Id with the given language base in the record. /// </exception> public ServiceAttribute GetAttributeById(ServiceAttributeId id, LanguageBaseItem language) { if (language == null) { throw new ArgumentNullException("language"); } ServiceAttributeId actualId = CreateLanguageBasedAttributeId(id, language.AttributeIdBase); ServiceAttribute attr = GetAttributeById(actualId); System.Diagnostics.Debug.Assert(attr != null); return(attr); }
public static ServiceAttributeId CreateLanguageBasedAttributeId(ServiceAttributeId id, ServiceAttributeId baseId) { System.Diagnostics.Debug.Assert(typeof(short) == Enum.GetUnderlyingType(typeof(ServiceAttributeId))); short offset = (short)baseId; ServiceAttributeId actualId = id + offset; // If either had the MSB set, then the result must also! if ((actualId < 0) ^ ((id < 0) || (baseId < 0))) { throw new OverflowException(); } return(actualId); }
private bool TryGetAttributeById(ServiceAttributeId id, out ServiceAttribute attribute) { foreach (ServiceAttribute curAttr in m_attributes) { if (curAttr.Id == id) { attribute = curAttr; System.Diagnostics.Debug.Assert(attribute != null); return(true); } }//for attribute = null; return(false); }
public String GetMultiLanguageStringAttributeById(ServiceAttributeId id, LanguageBaseItem language) { if (language == null) { throw new ArgumentNullException("language"); } ServiceAttributeId actualId = CreateLanguageBasedAttributeId(id, language.AttributeIdBase); ServiceAttribute attr = GetAttributeById(actualId); ServiceElement element = attr.Value; // (No need to check that element is of type TextString, that's handled inside the following). String str = element.GetValueAsString(language); return(str); }
public LanguageBaseItem GetPrimaryLanguageBaseItem() { LanguageBaseItem[] list = GetLanguageBaseList(); System.Diagnostics.Debug.Assert(list != null); const ServiceAttributeId PrimaryBaseId = (ServiceAttributeId)0x0100; foreach (LanguageBaseItem item in list) { if (item.AttributeIdBase == PrimaryBaseId) { return(item); } }//for return(null); }
// Check if the current field has the supplied value. private static string _GetNameIfMatches(ServiceAttributeId id, System.Reflection.FieldInfo curField) { object rawValue; // Does this require less permissions than the GetValue version. rawValue = curField.GetRawConstantValue(); ServiceAttributeId fieldValue = (ServiceAttributeId)rawValue; if (fieldValue == id) { string fieldName = curField.Name; return(fieldName); } return(null); }
/// <overloads> /// Returns the attribute with the given ID. /// </overloads> /// - /// <summary> /// Returns the attribute with the given ID. /// </summary> /// - /// <param name="id">The Attribute Id as a <see cref="T:InTheHand.Net.Bluetooth.ServiceAttributeId"/>.</param> /// - /// <returns>A <see cref="T:InTheHand.Net.Bluetooth.ServiceAttribute"/> holding /// the attribute with the specified ID. /// Is never <see langword="null"/>. /// </returns> /// - /// <exception cref="T:System.Collections.Generic.KeyNotFoundException"> /// There is no attribute with the given Id in the record. /// Throws <see cref="T:System.ArgumentException"/> in NETCFv1 /// </exception> public ServiceAttribute GetAttributeById(ServiceAttributeId id) { ServiceAttribute attribute; bool found = TryGetAttributeById(id, out attribute); if (!found) { #if V1 throw new ArgumentException(ErrorMsgNoAttributeWithId); #else throw new System.Collections.Generic.KeyNotFoundException(ErrorMsgNoAttributeWithId); #endif } System.Diagnostics.Debug.Assert(attribute != null); return(attribute); }
/// <summary> /// Add a custom attribute of simple type. /// </summary> /// - /// <remarks> /// <para>If the <paramref name="elementType"/> is a numerical type /// then this is equivalent to using /// <see cref="M:InTheHand.Net.Bluetooth.ServiceElement.CreateNumericalServiceElement(InTheHand.Net.Bluetooth.ElementType,System.Object)"/> /// otherwise the value is used directly in creating the /// <see cref="T:InTheHand.Net.Bluetooth.ServiceElement"/>. /// </para> /// </remarks> /// - /// <param name="id">The Attribute Id as a <see cref="T:InTheHand.Net.Bluetooth.ServiceAttributeId"/>.</param> /// <param name="elementType">The type of the element as an <see cref="T:InTheHand.Net.Bluetooth.ElementType"/>.</param> /// <param name="value">The value for the new element.</param> public void AddCustomAttribute(ServiceAttributeId id, ElementType elementType, object value) { ServiceElement e; ElementTypeDescriptor etd = ServiceRecordParser.GetEtdForType(elementType); if ((etd == ElementTypeDescriptor.UnsignedInteger || etd == ElementTypeDescriptor.TwosComplementInteger)) { e = ServiceElement.CreateNumericalServiceElement(elementType, value); } else { e = new ServiceElement(elementType, value); } this.AddCustomAttribute(new ServiceAttribute(id, e)); }
// Check if the current field has the supplied value. private static string _GetNameIfMatches(ServiceAttributeId id, System.Reflection.FieldInfo curField) { object rawValue; #if NETCF // This does the job too. As a static field the parameter is ignored. rawValue = curField.GetValue(null); #else // Does this require less permissions than the GetValue version. rawValue = curField.GetRawConstantValue(); #endif ServiceAttributeId fieldValue = (ServiceAttributeId)rawValue; if (fieldValue == id) { string fieldName = curField.Name; return(fieldName); } return(null); }
_GetNameIfMatchesMultiLang(ServiceAttributeId id, System.Reflection.FieldInfo curField, LanguageBaseItem[] langBaseList, out LanguageBaseItem applicableLangBase) { foreach (LanguageBaseItem curBaseItem in langBaseList) { ServiceAttributeId baseOffset = curBaseItem.AttributeIdBase; ServiceAttributeId realId = id; unchecked { realId -= baseOffset; } // (Theorically 'unchecked' above could allow wrong results but // only 0, 1, and 2, have "[StringWithLanguageBaseAttribute]", // and it would be an odd record that could produce those // integers for wrong reasons). string fieldName = _GetNameIfMatches(realId, curField); if (fieldName != null) { applicableLangBase = curBaseItem; return(fieldName); } }//foreach applicableLangBase = null; return(null); }
//-------------------------------------------------------------- /// <overloads> /// Determines whether a service attribute with the specified ID, /// and optional natural language, is in the List. /// </overloads> /// - /// <summary> /// Determines whether a service attribute with the specified ID is in the List. /// </summary> /// - /// <param name="id">The id of the service attribute to locate, as a /// <see cref="T:InTheHand.Net.Bluetooth.ServiceAttributeId"/>.</param> /// - /// <returns>true if item is found in the record; otherwise, false. </returns> public bool Contains(ServiceAttributeId id) { return(TryGetAttributeById(id, out _)); }
internal static ServiceRecord CreateServiceRecord(ref Structs.BtSdkRemoteServiceAttrStru attrs, IBluesoleilApi api) { ServiceRecordBuilder bldr = new ServiceRecordBuilder(); //-- Guid sc = BluetoothService.CreateBluetoothUuid(attrs.svc_class); bldr.AddServiceClass(sc); //-- string name = ParseServiceName(ref attrs); if (name.Length != 0) { bldr.ServiceName = name; } // byte?port = null; var extras = new List <ServiceAttribute>(); Debug.Assert(attrs.status == 0, "attrs.status: 0x" + attrs.status.ToString("X")); if (attrs.ext_attributes != IntPtr.Zero) { if (sc == BluetoothService.HumanInterfaceDevice) { var hidInfo = (Structs.BtSdkRmtHidSvcExtAttrStru_HACK)Marshal.PtrToStructure( attrs.ext_attributes, typeof(Structs.BtSdkRmtHidSvcExtAttrStru_HACK)); Debug.Assert(Marshal.SizeOf(typeof(Structs.BtSdkRmtHidSvcExtAttrStru_HACK)) == Marshal.SizeOf(hidInfo), "SizeOf x2"); Debug.Assert(hidInfo.size == Marshal.SizeOf(typeof(Structs.BtSdkRmtHidSvcExtAttrStru_HACK)) + Structs.BtSdkRmtHidSvcExtAttrStru_HACK.StackMiscountsPaddingSize, "Different sizes! hidInfo.size: " + hidInfo.size + ", SizeOf(): " + Marshal.SizeOf(typeof(Structs.BtSdkRmtHidSvcExtAttrStru_HACK))); // TO-DO Human Interface (HID) record: Use "mask" field, it's undocumented, check for real life values // With test SdpCreateAHumanInputDeviceRecordsAllTwoOfThree // which adds two out of three of {DeviceReleaseNumber,DeviceSubclass,CountryCode} // mask==0. So mask apparently applies to other fields! // So we check these three values for zero // and discard them if so! Debug.WriteLine(string.Format(CultureInfo.InvariantCulture, "HID.mask: {0:X}", hidInfo.mask)); var list = new List <ServiceAttribute>(); if (hidInfo.deviceReleaseNumber != 0) { list.Add( new ServiceAttribute(HidProfileAttributeId.DeviceReleaseNumber, new ServiceElement(ElementType.UInt16, hidInfo.deviceReleaseNumber))); } if (hidInfo.deviceSubclass != 0) { list.Add( new ServiceAttribute(HidProfileAttributeId.DeviceSubclass, new ServiceElement(ElementType.UInt8, hidInfo.deviceSubclass))); } if (hidInfo.countryCode != 0) { list.Add( new ServiceAttribute(HidProfileAttributeId.CountryCode, new ServiceElement(ElementType.UInt8, hidInfo.countryCode))); } // TO-DO HID other... extras.AddRange(list); } else if (sc == BluetoothService.PnPInformation) { var deviceInfo = (Structs.BtSdkRmtDISvcExtAttrStru)Marshal.PtrToStructure( attrs.ext_attributes, typeof(Structs.BtSdkRmtDISvcExtAttrStru)); Debug.Assert(Marshal.SizeOf(typeof(Structs.BtSdkRmtDISvcExtAttrStru)) == Marshal.SizeOf(deviceInfo), "SizeOf x2"); Debug.Assert(deviceInfo.size == Marshal.SizeOf(typeof(Structs.BtSdkRmtDISvcExtAttrStru)) + Structs.BtSdkRmtDISvcExtAttrStru.StackMiscountsPaddingSize, "Different sizes! deviceInfo.size: " + deviceInfo.size + ", Marshal.SizeOf: " + Marshal.SizeOf(typeof(Structs.BtSdkRmtDISvcExtAttrStru))); // TO-DO Device Info (PnP) record: Use "mask" field, it's undocumented, check for real life values //Debug.Assert(deviceInfo.mask == 0, "Is mask field in BtSdkRmtDISvcExtAttrStru ever set!!!, is here:" + deviceInfo.mask); Debug.WriteLine(string.Format(CultureInfo.InvariantCulture, "PnP/DI.mask: {0:X}", deviceInfo.mask)); // Like above (PnP) we see mask==0 for the fields we handle // here (six of). So we check these values // for zero and discard them if so! var list = new List <ServiceAttribute>(); if (deviceInfo.spec_id != 0) { list.Add( new ServiceAttribute(DeviceIdProfileAttributeId.SpecificationId, new ServiceElement(ElementType.UInt16, deviceInfo.spec_id))); } if (deviceInfo.vendor_id != 0) { list.Add( new ServiceAttribute(DeviceIdProfileAttributeId.VendorId, new ServiceElement(ElementType.UInt16, deviceInfo.vendor_id))); } if (deviceInfo.product_id != 0) { list.Add( new ServiceAttribute(DeviceIdProfileAttributeId.ProductId, new ServiceElement(ElementType.UInt16, deviceInfo.product_id))); } if (deviceInfo.version != 0) { list.Add( new ServiceAttribute(DeviceIdProfileAttributeId.Version, new ServiceElement(ElementType.UInt16, deviceInfo.version))); } if (true /* Zero means False here!! */) { list.Add( new ServiceAttribute(DeviceIdProfileAttributeId.PrimaryRecord, new ServiceElement(ElementType.Boolean, deviceInfo.primary_record))); } if (deviceInfo.vendor_id_source != 0) { list.Add( new ServiceAttribute(DeviceIdProfileAttributeId.VendorIdSource, new ServiceElement(ElementType.UInt16, deviceInfo.vendor_id_source))); } // TO-DO URLs... extras.AddRange(list); } else { // On testing we see this never working! For one device // with an ImagingResponder record the size of 0x18 and // not 0x8 as per definition, and the port value is wrong. // And for its PhonebookAccessPse record the size is // correctly 0x8, but again the port value is wrong! // var sppInfo = (Structs.BtSdkRmtSPPSvcExtAttrStru)Marshal.PtrToStructure( attrs.ext_attributes, typeof(Structs.BtSdkRmtSPPSvcExtAttrStru)); Debug.Assert(sppInfo.size == Marshal.SizeOf(typeof(Structs.BtSdkRmtSPPSvcExtAttrStru)), "Different sizes!"); port = sppInfo.server_channel; } api.Btsdk_FreeMemory(attrs.ext_attributes); }//if (attrs.ext_attributes != NULL) // Use a different API to try and get the RFCOMM port number as // the previous API is quite rubbish at doing that!! var svcB = new Structs.BtSdkAppExtSPPAttrStru(sc); var retSpp = api.Btsdk_SearchAppExtSPPService(attrs.dev_hdl, ref svcB); if (retSpp == BtSdkError.NO_SERVICE) // error { } else if (retSpp != BtSdkError.OK) // error { Debug.WriteLine("GetSvcRcds Btsdk_SearchAppExtSPPService ret: " + BluesoleilUtils.BtSdkErrorToString(retSpp)); } else // success { if (svcB.rf_svr_chnl != 0) { byte newPort = svcB.rf_svr_chnl; if (port.HasValue) { Debug.Assert(port.Value == newPort, "port: " + port.Value + ", newPort: " + newPort); } else { port = newPort; } } if (svcB.sdp_record_handle != 0) { bldr.AddCustomAttribute(new ServiceAttribute( UniversalAttributeId.ServiceRecordHandle, ServiceElement.CreateNumericalServiceElement(ElementType.UInt32, svcB.sdp_record_handle))); } #if DEBUG Debug.Assert(svcB.service_class_128 == sc, "svcSpp.service_class_128: " + svcB.service_class_128 + ", sc: " + sc); var snSpp = BluesoleilUtils.FromNameString(svcB.svc_name, StackConsts.BTSDK_SERVICENAME_MAXLENGTH); if (snSpp == null) { Debug.Assert(name == null || name.Length == 0, "svcSpp.svc_name: null" + ", name: " + name); } else if (snSpp.Length == 1) { // SearchAppExtSPPService doesn't handle Unicode // but Btsdk_BrowseRemoteServicesEx etc does. Debug.Assert(snSpp[0] == name[0], "svcSpp.svc_name: " + snSpp + ", name: " + name); } else { Debug.Assert(snSpp == name, "svcSpp.svc_name: " + snSpp + ", bldr.ServiceName: " + name); } #endif } // if (port.HasValue) { } else { bldr.ProtocolType = BluetoothProtocolDescriptorType.None; } if (extras.Count != 0) { bldr.AddCustomAttributes(extras); } // const ServiceAttributeId FakeDescr = (ServiceAttributeId)(-1); bldr.AddCustomAttribute(new ServiceAttribute(FakeDescr, new ServiceElement(ElementType.TextString, "<partial BlueSoleil decode>"))); ServiceRecord sr = bldr.ServiceRecord; if (port.HasValue) { Debug.Assert(bldr.ProtocolType == BluetoothProtocolDescriptorType.Rfcomm, "type=" + bldr.ProtocolType); ServiceRecordHelper.SetRfcommChannelNumber(sr, port.Value); } else { bldr.ProtocolType = BluetoothProtocolDescriptorType.None; } return(sr); }
//-------------------------------------------------------------- /// <overloads> /// Determines whether a service attribute with the specified ID, /// and optional natural language, is in the List. /// </overloads> /// - /// <summary> /// Determines whether a service attribute with the specified ID is in the List. /// </summary> /// - /// <param name="id">The id of the service attribute to locate, as a /// <see cref="T:InTheHand.Net.Bluetooth.ServiceAttributeId"/>.</param> /// - /// <returns>true if item is found in the record; otherwise, false. </returns> public bool Contains(ServiceAttributeId id) { ServiceAttribute tmp; return TryGetAttributeById(id, out tmp); }
//NODO No-(((TryGetAttributeById public? Also one with language param.))) private bool TryGetAttributeById(ServiceAttributeId id, out ServiceAttribute attribute) { foreach (ServiceAttribute curAttr in m_attributes) { if (curAttr.Id == id) { attribute = curAttr; System.Diagnostics.Debug.Assert(attribute != null); return true; } }//for attribute = null; return false; }
/// <summary> /// Returns the attribute with the given ID and natural language. /// </summary> /// - /// <param name="id">The id of the service attribute to locate, as a /// <see cref="T:InTheHand.Net.Bluetooth.ServiceAttributeId"/>.</param> /// <param name="language"> /// Which multi-language version of the string attribute to locate. /// </param> /// - /// <returns>A <see cref="T:InTheHand.Net.Bluetooth.ServiceAttribute"/> holding /// the attribute with the specified ID and language. /// Is never <see langword="null"/>. /// </returns> /// - /// <exception cref="T:System.Collections.Generic.KeyNotFoundException"> /// There is no attribute with the given Id with the given language base in the record. /// </exception> public ServiceAttribute GetAttributeById(ServiceAttributeId id, LanguageBaseItem language) { if (language == null) { throw new ArgumentNullException("language"); } ServiceAttributeId actualId = CreateLanguageBasedAttributeId(id, language.AttributeIdBase); ServiceAttribute attr = GetAttributeById(actualId); System.Diagnostics.Debug.Assert(attr != null); return attr; }
protected void GetRecordAttrInfo(out uint?hSR, out ServiceAttributeId attrId) { hSR = _hSR; attrId = _attrId; }
// Check if the current field has the supplied value. private static string _GetNameIfMatches(ServiceAttributeId id, System.Reflection.FieldInfo curField) { object rawValue; #if PocketPC // This does the job too. As a static field the parameter is ignored. rawValue = curField.GetValue(null); #else // Does this require less permissions than the GetValue version. rawValue = curField.GetRawConstantValue(); #endif ServiceAttributeId fieldValue = (ServiceAttributeId)rawValue; if (fieldValue == id) { string fieldName = curField.Name; return fieldName; } return null; }
public static string GetName(ServiceAttributeId id, Type[] attributeIdDefiningClasses, LanguageBaseItem[] langBaseList, out LanguageBaseItem applicableLangBase) { if (attributeIdDefiningClasses == null) { throw new ArgumentNullException("attributeIdDefiningClasses"); } //HACK if (langBaseList == null) { if (langBaseList == null) { throw new ArgumentNullException("langBaseList"); } // Foreach: class that defines AttributeId enum. // Foreach: AttributeId enum field in that class. // Check whether its value matches the one being searched for, and return if so. // foreach (Type curDefiningType in attributeIdDefiningClasses) { //if (!(curDefiningType.IsSealed && curDefiningType.IsAbstract)) { } //---- System.Reflection.FieldInfo[] fieldArr = curDefiningType.GetFields( // With Public, no permissions required, apparently. System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static); foreach (System.Reflection.FieldInfo curField in fieldArr) { if (curField.FieldType == typeof(ServiceAttributeId)) { // A multi-language attribute or a just a normal one? Object[] dotnetAtttrs = curField.GetCustomAttributes(typeof(StringWithLanguageBaseAttribute), false); if (dotnetAtttrs.Length != 0) { System.Diagnostics.Debug.Assert(dotnetAtttrs.Length == 1, "Not that it's a problem for us at all, but that Attribute should only be applied once."); string name = _GetNameIfMatchesMultiLang(id, curField, langBaseList, out applicableLangBase); if (name != null) { return name; } } else { // No just a normal Attribute, not language base offsetting. string name = _GetNameIfMatches(id, curField); if (name != null) { applicableLangBase = null; return name; } }//else } }//foreach }//foreach // Not found. applicableLangBase = null; return null; }
/// <summary> /// Initialize a new instance of the <see cref="T:InTheHand.Net.Bluetooth.LanguageBaseItem"/> class. /// </summary> /// - /// <param name="naturalLanguage">The Natural Language field of the entry. /// Some example values are 0x656E which is "en", and 0x6672 which is "fr". /// </param> /// <param name="encodingId">The IETF Charset identifier for this language. /// e.g. 3 for US-ASCII and 106 for UTF-8, /// see <see cref="P:InTheHand.Net.Bluetooth.LanguageBaseItem.EncodingId"/> /// </param> /// <param name="baseAttributeId">The base Attribute Id for this language /// in the record. /// e.g. 0x100 for the Primary language. /// </param> public LanguageBaseItem(Int16 naturalLanguage, Int16 encodingId, ServiceAttributeId baseAttributeId) : this(unchecked ((UInt16)naturalLanguage), unchecked ((UInt16)encodingId), baseAttributeId) { }
private int CreateAttrId(ServiceAttributeId attrId, byte[] buf, int offset) { ServiceElement dummyElement = new ServiceElement( ElementType.UInt16, unchecked((UInt16)attrId)); return CreateElement(dummyElement, buf, offset); }
//-------------------------------------------------------------- /// <summary> /// Initializes a new instance of the <see cref="T:InTheHand.Net.Bluetooth.ServiceAttribute"/> class. /// </summary> /// - /// <param name="id">The Attribute Id as a <see cref="T:InTheHand.Net.Bluetooth.ServiceAttributeId"/>.</param> /// <param name="value">The value as a <see cref="T:InTheHand.Net.Bluetooth.ServiceElement"/>.</param> public ServiceAttribute(ServiceAttributeId id, ServiceElement value) { m_id = id; m_element = value; }
/// <summary> /// Produce a 'dump' of the given record, including attribute names etc to the given /// <see cref="T:System.IO.TextWriter"/>. /// </summary> /// - /// <remarks> /// <para>The system has built-in a set of mappings from Service Class to /// its Attribute IDs. This is supplied by the /// <see cref="T:InTheHand.Net.Bluetooth.MapServiceClassToAttributeIdList"/> class, /// and contains the Attribute IDs defined in the base SDP specification as /// well as in Bluetooth Profiles specification e.g. ObjectPushProfile, Headset, /// Panu, etc. /// If however the record being decoded is a custom one then a set of extra /// Attribute Id definitions can be supplied in the /// <paramref name="attributeIdEnumDefiningTypes"/> parameter. /// The Attribute IDs for a particular Service Class /// should be defined in a static class and the set of such classes should /// be passed as their <see cref="T:System.Type"/> object. e.g. /// <code lang="C#"> /// static class FooAttributeId /// { /// public const ServiceAttributeId BarName = (ServiceAttributeId)0x0300; /// } /// /// … /// ServiceRecordUtilities.Dump(writer, myRecord, typeof(FooAttributeId)); /// … /// </code> /// </para> /// </remarks> /// - /// <param name="writer">A <see cref="T:System.IO.TextWriter"/> where the 'dump' /// text is to be written.</param> /// <param name="record">A <see cref="T:InTheHand.Net.Bluetooth.ServiceRecord"/> to be dumped.</param> /// <param name="attributeIdEnumDefiningTypes"> /// An optional array of <see cref="T:System.Type"/> specifing a set of Ids /// for the attributes contained in this record. See the /// </param> /// <seealso cref="M:InTheHand.Net.Bluetooth.ServiceRecordUtilities.Dump(InTheHand.Net.Bluetooth.ServiceRecord,System.Type[])"/> public static void Dump(System.IO.TextWriter writer, ServiceRecord record, params Type[] attributeIdEnumDefiningTypes) { if (writer == null) { throw new ArgumentNullException("writer"); } if (record == null) { throw new ArgumentNullException("record"); } // // .... // Get the AttributeIdEnumDefiningType for the services contained in the record. Type[] recordSpecificAttributeIdEnumDefiningTypes = GetServiceClassSpecificAttributeIdEnumDefiningType(record); // // Prepend the Universal Attribute Id definition class to the supplied list. Type[] allAttributeIdEnumDefiningTypes; allAttributeIdEnumDefiningTypes = CombineAttributeIdEnumDefiningTypes(attributeIdEnumDefiningTypes, recordSpecificAttributeIdEnumDefiningTypes); // LanguageBaseItem[] langBaseList = record.GetLanguageBaseList(); // bool firstAttr = true; foreach (ServiceAttribute attr in record) { if (!firstAttr) { writer.WriteLine(); } ServiceAttributeId id = (ServiceAttributeId)attr.Id; LanguageBaseItem applicableLangBase; string name = AttributeIdLookup.GetName(id, allAttributeIdEnumDefiningTypes, langBaseList, out applicableLangBase); if (name == null) { writer.WriteLine("AttrId: 0x{0:X4}", unchecked ((ushort)attr.Id)); } else { writer.WriteLine("AttrId: 0x{0:X4} -- {1}", (ushort)attr.Id, name); } //---- if (attr.Value.ElementType == ElementType.TextString) { DumpString(writer, 0, attr.Value, applicableLangBase); } else { DumpElement(writer, 0, attr.Value); } // Now print descriptive information for some cases. // e.g. for PDL: "( ( L2Cap ), ( Rfcomm, ChannelNumber=1 ), ( Obex ) )" if (id == AttributeIds.UniversalAttributeId.ProtocolDescriptorList) { DumpProtocolDescriptorList(writer, 0, attr.Value); } if (id == AttributeIds.UniversalAttributeId.AdditionalProtocolDescriptorLists) { DumpAdditionalProtocolDescriptorLists(writer, 0, attr.Value); } //TODO (( DumpLanguageBaseAttributeIdList, use ParseListFromElementSequence )) firstAttr = false; }//for }
public String GetMultiLanguageStringAttributeById(ServiceAttributeId id, LanguageBaseItem language) { if (language == null) { throw new ArgumentNullException("language"); } ServiceAttributeId actualId = CreateLanguageBasedAttributeId(id, language.AttributeIdBase); ServiceAttribute attr = GetAttributeById(actualId); ServiceElement element = attr.Value; // (No need to check that element is of type TextString, that's handled inside the following). String str = element.GetValueAsString(language); return str; }
public static ServiceAttributeId CreateLanguageBasedAttributeId(ServiceAttributeId id, ServiceAttributeId baseId) { System.Diagnostics.Debug.Assert(typeof(short) == Enum.GetUnderlyingType(typeof(ServiceAttributeId))); short offset = (short)baseId; ServiceAttributeId actualId = id + offset; // If either had the MSB set, then the result must also! if ((actualId < 0) ^ ((id < 0) || (baseId < 0))) { throw new OverflowException(); } return actualId; }
public LanguageBaseItem(String language, UInt16 encodingId, ServiceAttributeId baseAttributeId) : this(GetLanguageIdStringAsBytes(language), encodingId, baseAttributeId) { }
//-------------------------------------------------------------- /// <summary> /// Determines whether a TextString service attribute with the specified ID /// and natural language /// is in the List. /// </summary> /// - /// <param name="id">The id of the service attribute to locate, as a /// <see cref="T:InTheHand.Net.Bluetooth.ServiceAttributeId"/>.</param> /// <param name="language"> /// Which multi-language version of the string attribute to locate. /// </param> /// - /// <returns>true if item is found in the record; otherwise, false. </returns> public bool Contains(ServiceAttributeId id, LanguageBaseItem language) { if (language == null) { throw new ArgumentNullException("language"); } ServiceAttributeId actualId = CreateLanguageBasedAttributeId(id, language.AttributeIdBase); ServiceAttribute tmp; bool found = TryGetAttributeById(actualId, out tmp); return found && (tmp.Value.ElementType == ElementType.TextString); }
/// <summary> /// Initialize an a new instance of the <see cref="T:LanguageBaseItem"/> class. /// </summary> public LanguageBaseItem(String language, Int16 encodingId, ServiceAttributeId baseAttributeId) : this(GetLanguageIdStringAsBytes(language), unchecked((UInt16)encodingId), baseAttributeId) { }
/// <overloads> /// Returns the attribute with the given ID. /// </overloads> /// - /// <summary> /// Returns the attribute with the given ID. /// </summary> /// - /// <returns>A <see cref="T:InTheHand.Net.Bluetooth.ServiceAttribute"/> holding /// the attribute with the specified ID. /// Is never <see langword="null"/>. /// </returns> /// - /// <exception cref="T:System.Collections.Generic.KeyNotFoundException"> /// There is no attribute with the given Id in the record. /// Throws <see cref="T:System.ArgumentException"/> in NETCFv1 /// </exception> public ServiceAttribute GetAttributeById(ServiceAttributeId id) { ServiceAttribute attribute; bool found = TryGetAttributeById(id, out attribute); if (!found) { #if V1 throw new ArgumentException(ErrorMsgNoAttributeWithId); #else throw new System.Collections.Generic.KeyNotFoundException(ErrorMsgNoAttributeWithId); #endif } System.Diagnostics.Debug.Assert(attribute != null); return attribute; }
/// <summary> /// Initialize an a new instance of the <see cref="T:LanguageBaseItem"/> class. /// </summary> public LanguageBaseItem(Int16 naturalLanguage, Int16 encodingId, ServiceAttributeId baseAttributeId) :this(unchecked((UInt16)naturalLanguage), unchecked((UInt16)encodingId), baseAttributeId) { }
/// <summary> /// Initialize a new instance of the <see cref="T:InTheHand.Net.Bluetooth.LanguageBaseItem"/> class. /// </summary> /// - /// <param name="naturalLanguage">The Natural Language field of the entry. /// Some example values are "en", and "fr". /// </param> /// <param name="encodingId">The IETF Charset identifier for this language. /// e.g. 3 for US-ASCII and 106 for UTF-8, /// see <see cref="P:InTheHand.Net.Bluetooth.LanguageBaseItem.EncodingId"/> /// </param> /// <param name="baseAttributeId">The base Attribute Id for this language /// in the record. /// e.g. 0x100 for the Primary language. /// </param> public LanguageBaseItem(String naturalLanguage, Int16 encodingId, ServiceAttributeId baseAttributeId) : this(GetLanguageIdStringAsBytes(naturalLanguage), unchecked ((UInt16)encodingId), baseAttributeId) { }
public String GetPrimaryMultiLanguageStringAttributeById(ServiceAttributeId id) { LanguageBaseItem lang = this.GetPrimaryLanguageBaseItem(); if (lang == null) { lang = LanguageBaseItem.CreateEnglishUtf8PrimaryLanguageItem(); } return GetMultiLanguageStringAttributeById(id, lang); }
_GetNameIfMatchesMultiLang(ServiceAttributeId id, System.Reflection.FieldInfo curField, LanguageBaseItem[] langBaseList, out LanguageBaseItem applicableLangBase) { foreach (LanguageBaseItem curBaseItem in langBaseList) { ServiceAttributeId baseOffset = curBaseItem.AttributeIdBase; ServiceAttributeId realId = id; realId -= baseOffset; string fieldName = _GetNameIfMatches(realId, curField); if (fieldName != null) { applicableLangBase = curBaseItem; return fieldName; } }//foreach applicableLangBase = null; return null; }
public ServiceRecord[] GetServiceRecords() { Debug.Assert(m_request.searchScope == SdpSearchScope.Anywhere, "unexpected searchScope: " + m_request.searchScope); int classInSCL, classAnywhere; if (m_records == null) { m_records = new List <ServiceRecord>(); SdpDiscoveryRecordsBufferBase.SimpleInfo[] infoArr = GetSimpleInfo(); foreach (SdpDiscoveryRecordsBufferBase.SimpleInfo info in infoArr) { classInSCL = classAnywhere = 0; //Utils.MiscUtils.Trace_WriteLine("fake int: {0}", info.fake); ServiceRecordBuilder bldr = new ServiceRecordBuilder(); const ServiceAttributeId FakeDescr = (ServiceAttributeId)(-1); bldr.AddCustomAttribute(new ServiceAttribute(FakeDescr, new ServiceElement(ElementType.TextString, "<partial Widcomm decode>"))); //-- bldr.AddServiceClass(info.serviceUuid); if (m_request.serviceGuid == info.serviceUuid) { ++classInSCL; } //-- if (info.serviceNameWchar != IntPtr.Zero) { string name = Marshal.PtrToStringUni(info.serviceNameWchar); if (name.Length != 0) { bldr.ServiceName = name; } } else if (info.serviceNameChar != IntPtr.Zero) { // PtrToStringAnsi is not supported on NETCF. The field // is not used by the native code there so that's ok. #if NETCF Debug.Fail("Don't expect 'serviceNameChar' on PPC."); #else string name = Marshal.PtrToStringAnsi(info.serviceNameChar); if (name.Length != 0) { bldr.ServiceName = name; } #endif } //-- if (info.scn == -1) { bldr.ProtocolType = BluetoothProtocolDescriptorType.None; } //-- switch (bldr.ProtocolType) { case BluetoothProtocolDescriptorType.GeneralObex: Debug.Fail("GEOP untested"); if (m_request.serviceGuid == BluetoothService.ObexProtocol) { ++classAnywhere; } goto case BluetoothProtocolDescriptorType.Rfcomm; case BluetoothProtocolDescriptorType.Rfcomm: if (m_request.serviceGuid == BluetoothService.RFCommProtocol) { ++classAnywhere; } if (m_request.serviceGuid == BluetoothService.L2CapProtocol) { ++classAnywhere; } break; case BluetoothProtocolDescriptorType.None: // We'd better assume L2CAP in the PDL or we'd skip too many // e.g. the SDP server record! if (m_request.serviceGuid == BluetoothService.L2CapProtocol) { ++classAnywhere; } break; } //-- ServiceRecord sr = bldr.ServiceRecord; if (info.scn != -1) { Debug.Assert(bldr.ProtocolType == BluetoothProtocolDescriptorType.Rfcomm, "type=" + bldr.ProtocolType); ServiceRecordHelper.SetRfcommChannelNumber(sr, checked ((byte)info.scn)); } if (classInSCL > 0 || classAnywhere > 0) { Utils.MiscUtils.Trace_WriteLine("Adding record"); m_records.Add(sr); } else // COVERAGE { Utils.MiscUtils.Trace_WriteLine("Skipping record"); } } } return(m_records.ToArray()); }
//-------------------------------------------------------------- /// <summary> /// Initializes a new instance of the <see cref="T:InTheHand.Net.Bluetooth.ServiceAttribute"/> class. /// </summary> public ServiceAttribute(ServiceAttributeId id, ServiceElement value) { m_id = id; m_element = value; }
public void BadBaseAttrId() { ServiceAttributeId badBase = 0; new LanguageBaseItem(1, 2, badBase); }