एआईडीएल वीएचएएल इंटरफ़ेस

एआईडीएल वीएचएएल को android.hardware.automotive.vehicle namespace में तय किया गया है. वीएचएएल इंटरफ़ेस को IVehicle.aidl पर तय किया गया है. जब तक बताया न जाए, तब तक सभी तरीकों को किसी खास VHAL वर्शन के लिए लागू करना होगा.

वर्शन

Android वर्शन वीएचएएल का नया वर्शन VHAL प्रॉपर्टी का नया वर्शन VHAL का कम से कम वह वर्शन जो इस सुविधा के साथ काम करता हो
Android 16 V4 V4 V1
Android 15 V3 V3 V1
Android 14 V2 V2 V1
Android 13 V1 (वीएचएएल प्रॉपर्टी इंटरफ़ेस को अलग नहीं किया गया है) V1

हमारा सुझाव है कि किसी Android वर्शन के लिए, वीएचएएल के नए वर्शन को लागू किया जाए.

फ़ंक्शन और कॉलबैक

वीएचएएल फ़ंक्शन के बारे में जानकारी, IVehicle.aidl पर दी गई है.

तरीका
VehiclePropConfigs getAllPropConfigs()
यह फ़ंक्शन, उन सभी प्रॉपर्टी कॉन्फ़िगरेशन की सूची दिखाता है जो इस व्हीकल एचएएल के साथ काम करते हैं.
VehiclePropConfigs getPropConfigs(in int[] props)
यह फ़ंक्शन, दिए गए प्रॉपर्टी आईडी के लिए, प्रॉपर्टी कॉन्फ़िगरेशन की सूची दिखाता है.
void getValues(IVehicleCallback callback, in GetValueRequests requests)
वाहन की प्रॉपर्टी की वैल्यू को एसिंक्रोनस तरीके से पाएं. यह GetValueRequest के बैच को एसिंक्रोनस तरीके से हैंडल करता है. नतीजा, कॉलबैक के onGetValues तरीके से डिलीवर किया जाता है.
void setValues(IVehicleCallback callback, in SetValueRequests requests)
वाहन की प्रॉपर्टी की वैल्यू को एसिंक्रोनस तरीके से सेट करें. यह SetValueRequest के बैच को एसिंक्रोनस तरीके से हैंडल करता है. नतीजा, कॉलबैक के onSetValues तरीके से डिलीवर किया जाता है.
void subscribe(in IVehicleCallback callback, in SubscribeOptions[] options, int maxSharedMemoryFileCount)
यह प्रॉपर्टी के इवेंट के लिए सदस्यता लेता है. इसके लिए, तय किए गए विकल्पों का इस्तेमाल किया जाता है. सदस्यता लेने के विकल्पों में ये शामिल हैं: प्रॉपर्टी आईडी, प्रॉपर्टी एरिया आईडी, और हर्ट्ज़ में सैंपल रेट (लगातार चलने वाली प्रॉपर्टी के लिए). maxSharedMemoryFileCount का इस्तेमाल नहीं किया जाता.
void unsubscribe(in IVehicleCallback callback, in int[] propIds)
यह फ़ंक्शन, पहले से सब्सक्राइब की गई प्रॉपर्टी के इवेंट को चुनिंदा प्रॉपर्टी के लिए अनसब्सक्राइब करता है.
returnSharedMemory(in IVehicleCallback callback, long sharedMemoryId)
इस्तेमाल नहीं किया गया और इसे no-op के तौर पर लागू किया जा सकता है.
(Android 16 में नई सुविधा)
SupportedValuesListResults getSupportedValuesLists(in List propIdAreaIds)
यह सुविधा, तय किए गए प्रॉपर्टी आईडी और एरिया आईडी के जोड़े के लिए, काम करने वाली वैल्यू की सूचियां दिखाती है.
इसे वीएचएएल V4 में पेश किया गया था.
(Android 16 में नई सुविधा)
MinMaxSupportedValueResults getMinMaxSupportedValue(in List propIdAreaIds)
इससे, तय किए गए प्रॉपर्टी आईडी और एरिया आईडी के जोड़े के लिए, कम से कम और ज़्यादा से ज़्यादा वैल्यू मिलती हैं.
इसे वीएचएएल V4 में पेश किया गया था.
void registerSupportedValueChangeCallback(in IVehicleCallback callback, in List propIdAreaIds)
यह एक कॉलबैक रजिस्टर करता है. इसे तब कॉल किया जाता है, जब इस्तेमाल की जा सकने वाली वैल्यू बदल जाती हैं.
इसे वीएचएएल V4 में पेश किया गया था.
void unregisterSupportedValueChangeCallback(in IVehicleCallback callback, in List propIdAreaIds)
यह वैल्यू में बदलाव करने के लिए इस्तेमाल किए जा सकने वाले कॉलबैक को अनरजिस्टर करता है.
इसे वीएचएएल V4 में पेश किया गया था.

कॉलबैक को IVehicleCallback.aidl पर तय किया जाता है और इनमें ये तरीके शामिल होते हैं.

तरीका
oneway void onGetValues(in GetValueResults responses)
getValues फ़ंक्शन के लिए कॉलबैक, ताकि वैल्यू पाने के नतीजे दिखाए जा सकें. जब फ़ेच की जाने वाली कुछ वैल्यू तैयार हो जाती हैं, तब इस फ़ंक्शन को कॉल किया जाता है.
oneway void onSetValues(in SetValueResults responses)
सेट की गई वैल्यू के नतीजे देने के लिए, setValues फ़ंक्शन के लिए कॉलबैक. इस फ़ंक्शन को तब कॉल किया जाता है, जब VHAL ने प्रॉपर्टी सेट करने के कुछ अनुरोधों को पूरा कर लिया हो.
oneway void onPropertyEvent(in VehiclePropValues propValues, int sharedMemoryFileCount)
प्रॉपर्टी अपडेट इवेंट की रिपोर्टिंग के लिए कॉलबैक.
CONTINUOUS प्रॉपर्टी के लिए, प्रॉपर्टी इवेंट, सदस्यता के लिए सैंपल रेट के आधार पर होता है. यह रेट, हर्ट्ज़ या वाहन बस मैसेज की फ़्रीक्वेंसी में होता है. प्रॉपर्टी इवेंट तब भी हो सकता है, जब किसी प्रॉपर्टी का स्टेटस बदलता है. उदाहरण के लिए, 'उपलब्ध नहीं है' से 'उपलब्ध है' पर सेट करना.
ON_CHANGE प्रॉपर्टी के लिए, प्रॉपर्टी इवेंट तब होता है, जब किसी प्रॉपर्टी की वैल्यू या स्टेटस बदलता है.
इस एट्रिब्यूट का इस्तेमाल, प्रॉपर्टी के स्टेटस में बदलाव से जुड़े इवेंट डिलीवर करने के लिए भी किया जाना चाहिए. उदाहरण के लिए, जब प्रॉपर्टी उपलब्ध न हो या उसे पढ़ने में गड़बड़ी हो, तब 'उपलब्ध नहीं है' या 'गड़बड़ी' स्टेटस और खाली वैल्यू वाला VehiclePropValue डिलीवर किया जाना चाहिए.
SharedMemoryFileCount हमेशा 0 होता है.
oneway void onPropertySetError(in VehiclePropErrors errors)
यह एसिंक्रोनस प्रॉपर्टी सेट करने से जुड़ी उन गड़बड़ियों की रिपोर्टिंग के लिए कॉलबैक है जिनके लिए कोई सेट अनुरोध नहीं किया गया है. अगर हमें पता है कि किस सेट अनुरोध के लिए गड़बड़ी हुई है, तो इसके बजाय गड़बड़ी के नतीजे के साथ onSetValues का इस्तेमाल किया जाना चाहिए.
oneway void onSupportedValueChange(in List propIdAreaIds)
यह कॉलबैक, इस्तेमाल की जा सकने वाली कम से कम और ज़्यादा से ज़्यादा वैल्यू या इस्तेमाल की जा सकने वाली वैल्यू की सूची में हुए बदलावों की रिपोर्टिंग के लिए होता है. कॉल करने वाले व्यक्ति को अपडेट की गई वैल्यू पाने के लिए, getMinMaxSupportedValue या getSupportedValuesLists को कॉल करना होगा.

वीएचएएल के लागू होने की पुष्टि, वीएचएएल वीटीएस VtsHalAutomotiveVehicle_TargetTest.cpp पर करता है.

इस टेस्ट से यह पुष्टि की जाती है कि बुनियादी तरीकों को सही तरीके से लागू किया गया है और प्रॉपर्टी के साथ काम करने वाले कॉन्फ़िगरेशन सही हैं. यह टेस्ट, डिवाइस पर मौजूद सभी VHAL इंस्टेंस के ख़िलाफ़ किया जाता है. हालांकि, AAOS सिर्फ़ डिफ़ॉल्ट इंस्टेंस (android.hardware.automotive.vehicle.IVehicle/default) का इस्तेमाल करता है

वाहन की प्रॉपर्टी की वैल्यू

हर प्रॉपर्टी की वैल्यू के बारे में बताने के लिए, VehiclePropValue स्ट्रक्चर का इस्तेमाल करें. इसमें ये फ़ील्ड होते हैं:

फ़ील्ड ब्यौरा
timestamp यह टाइमस्टैंप, इवेंट के होने का समय दिखाता है. साथ ही, यह SystemClock.elapsedRealtimeNano() घड़ी के साथ सिंक होता है.
prop इस वैल्यू के लिए प्रॉपर्टी आईडी.
areaid इस वैल्यू के लिए क्षेत्र का आईडी. यह क्षेत्र, क्षेत्र के आईडी कॉन्फ़िगरेशन में दिए गए उन क्षेत्रों में से एक होना चाहिए जहां यह सुविधा काम करती है. इसके अलावा, ग्लोबल प्रॉपर्टी के लिए 0 का इस्तेमाल किया जा सकता है.
value यह एक डेटा स्ट्रक्चर है, जिसमें प्रॉपर्टी की असल वैल्यू होती है. प्रॉपर्टी टाइप के आधार पर, इस फ़ील्ड में मौजूद एक या उससे ज़्यादा फ़ील्ड का इस्तेमाल, असल वैल्यू को सेव करने के लिए किया जाता है. उदाहरण के लिए, value.int32Values में मौजूद पहले एलिमेंट का इस्तेमाल, Int32 टाइप की प्रॉपर्टी के लिए किया जाता है. ज़्यादा जानकारी के लिए, प्रॉपर्टी के कॉन्फ़िगरेशन देखें.
status प्रॉपर्टी को पढ़ने की स्थिति. पढ़ने/लिखने की प्रॉपर्टी के लिए, यह लिखने पर भी लागू हो सकता है. हालांकि, इसकी गारंटी नहीं है. उदाहरण के लिए, हो सकता है कि प्रॉपर्टी पढ़ने के लिए उपलब्ध हो, लेकिन लिखने के लिए उपलब्ध न हो. ऐसे मामले में, स्टेटस AVAILABLE होता है और वैल्यू फ़ील्ड में मान्य जानकारी होती है. संभावित स्टेटस के लिए, VehiclePropertyStatus देखें.

एसिंक्रोनस getValues और setValues

getValues और setValues कार्रवाइयां एसिंक्रोनस तरीके से की जाती हैं. इसका मतलब है कि फ़ंक्शन, get या set की कार्रवाई पूरी होने से पहले ही वैल्यू दिखा सकता है. कार्रवाई के नतीजे (उदाहरण के लिए, getValues के लिए प्रॉपर्टी वैल्यू और setValues के लिए सफलता या गड़बड़ी की स्थिति) को, तर्क के तौर पर पास किए गए कॉलबैक के ज़रिए डिलीवर किया जाता है.

अनुरोध को हैंडल करने वाली बाइंडर थ्रेड में, नतीजे के आधार पर लागू करने की प्रोसेस को ब्लॉक नहीं किया जाना चाहिए. इसके बजाय, हमारा सुझाव है कि अनुरोध को अनुरोध की कतार में सेव करें. साथ ही, अनुरोधों को एसिंक्रोनस तरीके से हैंडल करने के लिए, अलग हैंडलर थ्रेड का इस्तेमाल करें. ज़्यादा जानकारी के लिए, रेफ़रंस इंप्लीमेंटेशन देखें.

पहली इमेज. एसिंक्रोनस प्रोसेस.

बड़े पार्सल किए जा सकने वाले ऑब्जेक्ट

XXXs नाम वाले सभी स्ट्रक्चर, जैसे कि VehiclePropConfigs, SetValueRequests, और VehiclePropValues को LargeParcelable (या StableLargeParcelable) कहा जाता है. हर स्ट्रक्चर, वैल्यू की एक सूची दिखाता है. इसका इस्तेमाल, बड़े डेटा को पास करने के लिए किया जाता है. यह डेटा, बाइंडर की सीमाओं (LargeParcelable लाइब्रेरी के लागू होने पर 4 केबी) से ज़्यादा हो सकता है. इन सभी का स्ट्रक्चर एक जैसा होता है. इसमें ये फ़ील्ड शामिल होते हैं.

दिशा-निर्देश ब्यौरा
payloads अगर वैल्यू का साइज़ बाइंडर की मेमोरी की सीमा के अंदर है, तो वैल्यू की सूची या खाली सूची.
sharedMemoryFd शेयर की गई मेमोरी फ़ाइल की ओर इशारा करने वाला फ़ाइल डिस्क्रिप्टर, जो वैल्यू की सूची बहुत बड़ी होने पर क्रम से लगाए गए पेलोड सेव करता है.

उदाहरण के लिए, VehiclePropConfigs को इस तरह से परिभाषित किया गया है:

parcelable VehiclePropConfigs {
    // The list of vehicle property configs if they fit the binder memory
    // limitation.
    VehiclePropConfig[] payloads;
    // Shared memory file to store configs if they exceed binder memory
    // limitation. Created by VHAL, readable only at client. Client could keep
    // the fd opened or keep the FD mapped to access configs.
    @nullable ParcelFileDescriptor sharedMemoryFd;
}

VehiclePropConfigs में या तो नॉन-एम्टी पेलोड या नॉन-नल sharedMemoryFd शामिल है.

  • अगर payloads खाली नहीं है, तो यह असल डेटा की सूची को सेव करता है. यह प्रॉपर्टी कॉन्फ़िगरेशन है.
  • अगर sharedMemoryFd शून्य नहीं है, तो इसमें शेयर की गई मेमोरी फ़ाइल होती है. यह VehiclePropConfigs के क्रम से लगाए गए स्ट्रक्चर को सेव करती है. इस स्ट्रक्चर में, पार्सल को क्रम से लगाने के लिए writeToParcel फ़ंक्शन का इस्तेमाल किया जाता है.

वीएचएएल के लिए Java क्लाइंट के तौर पर, Car Service, LargeParcelable के लिए सीरियलाइज़ेशन और डीसीरियलाइज़ेशन को मैनेज करती है. VHAL लागू करने और नेटिव क्लाइंट के लिए, LargeParcelable को LargeParcelable लाइब्रेरी के साथ क्रम से लगाया और क्रम से हटाया जाना चाहिए. इसके अलावा, ParcelableUtils.h में लाइब्रेरी के लिए काम की रैपर क्लास का इस्तेमाल किया जाना चाहिए.

उदाहरण के लिए, किसी बाइंडर से मिले getValues के अनुरोधों को पार्स करने वाले नेटिव क्लाइंट का अनुरोध यहां दिया गया है:

// 'requests' are from the binder.
GetValueRequests requests;
expected<LargeParcelableBase::BorrowedOwnedObject, ScopedAStatus> deserializedResults = fromStableLargeParcelable(requests);
if (deserializedResults.ok()) {
    const std::vector& getValueRequests = deserializedResults.value().getObject()->payloads;
    // Use the getValueRequests.
  } else {
    // handle error.
}

वीएचएएल को लागू करने का एक उदाहरण यहां दिया गया है. इसमें, बाइंडर के ज़रिए getValues के नतीजे भेजे जाते हैं:

std::vector results = getResults();
GetValueResults parcelableResults;
ScopedAStatus status = vectorToStableLargeParcelable(std::move(results), &parcelableResults);
if (status.isOk()) {
    // Send parcelableResults through callback.
} else {
    // Handle error.
}