.dex
फ़ाइल, Dalvik बाइटकोड के लिए ट्रांसपोर्ट फ़ॉर्मैट है. किसी फ़ाइल को मान्य .dex
फ़ाइल बनाने के लिए, उसमें कुछ सिंटैक्स और सिमेंटिक से जुड़ी पाबंदियां होती हैं. साथ ही, सिर्फ़ मान्य .dex फ़ाइलों के साथ काम करने के लिए, रनटाइम की ज़रूरत होती है.
.dex फ़ाइल की इंटिग्रिटी से जुड़ी सामान्य शर्तें
पूरी सुरक्षा से जुड़ी सामान्य पाबंदियां, .dex
फ़ाइल के बड़े स्ट्रक्चर से जुड़ी होती हैं. इनके बारे में .dex
फ़ॉर्मैट में पूरी जानकारी दी गई है.
पहचानकर्ता | ब्यौरा |
---|---|
G1 |
.dex फ़ाइल का magic नंबर, वर्शन 35 के लिए dex\n035\0 होना चाहिए. इसके अलावा, यह बाद के वर्शन के लिए भी ऐसा ही होना चाहिए.
|
G2 |
यह चेकसम, magic और checksum फ़ील्ड को छोड़कर, पूरी फ़ाइल के कॉन्टेंट का Adler-32 चेकसम होना चाहिए.
|
G3 |
हस्ताक्षर, magic ,
checksum , और signature को छोड़कर, फ़ाइल के पूरे कॉन्टेंट का SHA-1 हैश होना चाहिए.
|
G4 |
|
G5 |
|
G6 |
endian_tag की वैल्यू, इनमें से कोई एक होनी चाहिए:
ENDIAN_CONSTANT या REVERSE_ENDIAN_CONSTANT
|
G7 |
|
G8 |
map_off को छोड़कर, हेडर में मौजूद सभी ऑफ़सेट फ़ील्ड चार बाइट के अलाइन होने चाहिए.
|
G9 |
map_off फ़ील्ड में शून्य या डेटा सेक्शन का रेफ़रंस होना चाहिए. दूसरे मामले में, data सेक्शन मौजूद होना चाहिए.
|
G10 |
link , string_ids ,
type_ids , proto_ids , field_ids ,
method_ids , class_defs , और data सेक्शन, एक-दूसरे या हेडर पर ओवरलैप नहीं होने चाहिए.
|
G11 | अगर कोई मैप मौजूद है, तो हर मैप एंट्री का टाइप मान्य होना चाहिए. हर टाइप ज़्यादा से ज़्यादा एक बार दिख सकता है. |
G12 |
अगर कोई मैप मौजूद है, तो हर मैप एंट्री का ऑफ़सेट और साइज़ शून्य से ज़्यादा होना चाहिए. ऑफ़सेट, फ़ाइल के उस सेक्शन पर ले जाना चाहिए जिससे वह जुड़ा है.जैसे, string_id_item को string_ids सेक्शन पर ले जाना चाहिए. साथ ही, आइटम का साफ़ तौर पर या डिफ़ॉल्ट रूप से दिया गया साइज़, सेक्शन के असल कॉन्टेंट और साइज़ से मेल खाना चाहिए.
|
G13 |
अगर कोई मैप मौजूद है, तो मैप एंट्री n+1 का ऑफ़सेट, मैप एंट्री n plus than size of map entry n के ऑफ़सेट से ज़्यादा या उसके बराबर होना चाहिए. इसका मतलब है कि
एंट्री ओवरलैप नहीं होनी चाहिए और उन्हें कम से ज़्यादा के क्रम में लगाया जाना चाहिए.
|
G14 |
इन टाइप की एंट्री का ऑफ़सेट, चार बाइट के हिसाब से अलाइन होना चाहिए: string_id_item ,
type_id_item , proto_id_item ,
field_id_item ,
method_id_item , class_def_item ,
type_list , code_item ,
annotations_directory_item .
|
G15 |
हर हर रेफ़रंस वाले |
G16 |
हर type_id_item के लिए, descriptor_idx फ़ील्ड में string_ids सूची का मान्य रेफ़रंस होना चाहिए. रेफ़रंस वाली स्ट्रिंग, टाइप के लिए मान्य डिस्क्रिप्टर होनी चाहिए.
|
G17 |
हर proto_id_item के लिए, shorty_idx फ़ील्ड में string_ids सूची का मान्य रेफ़रंस होना चाहिए. रेफ़रंस की गई स्ट्रिंग, एक मान्य
शॉर्टी डिस्क्रिप्टर होनी चाहिए. साथ ही, return_type_idx फ़ील्ड, type_ids सेक्शन में एक मान्य इंडेक्स होना चाहिए. इसके अलावा, parameters_off फ़ील्ड, शून्य या data सेक्शन में ले जाने वाला मान्य ऑफ़सेट होना चाहिए. अगर यह शून्य से ज़्यादा है, तो पैरामीटर की सूची में
कोई भी अमान्य एंट्री नहीं होनी चाहिए.
|
G18 |
हर field_id_item के लिए, class_idx और type_idx , दोनों फ़ील्ड type_ids सूची में मान्य इंडेक्स होने चाहिए. class_idx के ज़रिए रेफ़र की गई एंट्री, ऐरे रेफ़रंस टाइप की नहीं होनी चाहिए. इसके अलावा, name_idx फ़ील्ड, string_ids सेक्शन में एक मान्य रेफ़रंस होना चाहिए. साथ ही, रेफ़र की गई एंट्री का कॉन्टेंट, MemberName स्पेसिफ़िकेशन के मुताबिक होना चाहिए.
|
G19 |
हर method_id_item के लिए, class_idx फ़ील्ड type_ids सेक्शन में एक मान्य इंडेक्स होना चाहिए. साथ ही, रेफ़रंस वाली एंट्री, ऐरे रेफ़रंस टाइप नहीं होनी चाहिए. proto_id फ़ील्ड, proto_ids सूची में मौजूद एक मान्य रेफ़रंस होना चाहिए. name_idx फ़ील्ड, string_ids सेक्शन में मौजूद किसी मान्य एंट्री का रेफ़रंस होना चाहिए. साथ ही, रेफ़र की गई एंट्री का कॉन्टेंट, MemberName से जुड़ी शर्तों के मुताबिक होना चाहिए.
|
G20 |
हर field_id_item के लिए, class_idx फ़ील्ड type_ids सूची में एक मान्य इंडेक्स होना चाहिए. रेफ़रंस वाली एंट्री, ऐरे रेफ़रंस टाइप की नहीं होनी चाहिए.
|
स्टैटिक बाइटकोड की सीमाएं
स्टैटिक कंस्ट्रेंट, बाइटकोड के अलग-अलग एलिमेंट पर लगने वाली पाबंदियां होती हैं. आम तौर पर, इनकी जांच कंट्रोल या डेटा-फ़्लो विश्लेषण की तकनीकों का इस्तेमाल किए बिना की जा सकती है.
पहचानकर्ता | ब्यौरा |
---|---|
A1 |
insns कलेक्शन खाली नहीं होना चाहिए.
|
A2 |
insns कलेक्शन में पहले ऑपरेंड कोड का इंडेक्स शून्य होना चाहिए.
|
A3 |
insns कलेक्शन में सिर्फ़ मान्य Dalvik ऑपरेंड कोड होने चाहिए.
|
A4 |
निर्देश n+1 का इंडेक्स, निर्देश n के इंडेक्स के बराबर होना चाहिए. साथ ही, संभावित ऑपरेंड को ध्यान में रखते हुए, निर्देश n की लंबाई भी इंडेक्स में शामिल होनी चाहिए.
|
A5 |
insns कलेक्शन में मौजूद आखिरी निर्देश, इंडेक्स
insns_size-1 पर खत्म होना चाहिए.
|
A6 |
सभी goto और if-<kind> टारगेट, एक ही तरीके में ऑपरेंड होने चाहिए.
|
A7 |
packed-switch निर्देश के सभी टारगेट, एक ही तरीके में ऑपरेंड होने चाहिए. टारगेट का साइज़ और सूची एक जैसी होनी चाहिए.
|
A8 |
sparse-switch निर्देश के सभी टारगेट, एक ही तरीके में ऑपरेंड होने चाहिए. उससे जुड़ी टेबल एक जैसी होनी चाहिए और कम से ज़्यादा के हिसाब से क्रम में होनी चाहिए.
|
A9 |
const-string और
const-string/jumbo निर्देशों का B ऑपरेंड, स्ट्रिंग कॉन्सटेंट पूल में एक मान्य इंडेक्स होना चाहिए.
|
A10 |
iget<kind> और
iput<kind> निर्देशों का C ऑपरेंड, फ़ील्ड कॉन्स्टेंट पूल में एक मान्य इंडेक्स होना चाहिए. रेफ़रंस वाली एंट्री में, किसी इंस्टेंस फ़ील्ड की जानकारी होनी चाहिए.
|
A11 |
sget<kind> और
sput<kind> निर्देशों का C ऑपरेंड, फ़ील्ड कॉन्स्टेंट पूल में एक मान्य इंडेक्स होना चाहिए. रेफ़रंस वाली एंट्री, स्टैटिक फ़ील्ड होनी चाहिए.
|
A12 |
invoke-virtual ,
invoke-super , invoke-direct , और
invoke-static निर्देशों का C ऑपरेंड,
मेथड कॉन्सटेंट पूल में एक मान्य इंडेक्स होना चाहिए.
|
A13 |
invoke-virtual/range ,
invoke-super/range , invoke-direct/range , और
invoke-static/range निर्देशों का B ऑपरेंड, मेथड कॉन्स्टेंट पूल में एक मान्य इंडेक्स होना चाहिए.
|
A14 |
जिस तरीके का नाम '<' से शुरू होता है उसे सिर्फ़ वीएम के ज़रिए शुरू किया जाना चाहिए, न कि .dex फ़ाइल से जनरेट हुए कोड से. इसका एकमात्र अपवाद इंस्टेंस को शुरू करने वाला फ़ंक्शन है, जिसे invoke-direct से शुरू किया जा सकता है.
|
A15 |
invoke-interface
निर्देश का C ऑपरेंड, मेथड कॉन्सटेंट पूल में एक मान्य इंडेक्स होना चाहिए. रेफ़रंस के तौर पर दिया गया method_id , किसी इंटरफ़ेस से जुड़ा होना चाहिए, न कि किसी क्लास से.
|
A16 |
invoke-interface/range
निर्देश का B ऑपरेंड, मेथड कॉन्सटेंट पूल में एक मान्य इंडेक्स होना चाहिए.
रेफ़रंस वाला method_id , किसी इंटरफ़ेस से जुड़ा होना चाहिए, न कि किसी क्लास से.
|
A17 |
const-class ,
check-cast , new-instance , और
filled-new-array/range निर्देशों का B ऑपरेंड, टाइप कॉन्स्टेंट पूल में एक मान्य इंडेक्स होना चाहिए.
|
A18 |
instance-of ,
new-array , और filled-new-array के C ऑपरेंड,
निर्देशों में टाइप कॉन्स्टेंट पूल में मान्य इंडेक्स होना चाहिए.
|
A19 |
new-array
निर्देश से बनाए गए ऐरे के डाइमेंशन, 256 से कम होने चाहिए.
|
A20 |
new निर्देश में ऐरे क्लास,
इंटरफ़ेस या ऐब्स्ट्रैक्ट क्लास का रेफ़रंस नहीं होना चाहिए.
|
A21 |
new-array निर्देश में बताए गए टाइप का रेफ़रंस नहीं होना चाहिए. साथ ही, यह टाइप मान्य होना चाहिए.
|
A22 |
किसी निर्देश में एक ही चौड़ाई (बिना जोड़े) वाले सभी रजिस्टर, मौजूदा तरीके के लिए मान्य होने चाहिए. इसका मतलब है कि
उनके इंडेक्स, registers_size से छोटे और नॉन-नेगेटिव होने चाहिए.
|
A23 |
किसी निर्देश में डबल-विड्थ (पेयर) के तौर पर बताए गए सभी रजिस्टर, मौजूदा तरीके के लिए मान्य होने चाहिए. इसका मतलब है कि उनके इंडेक्स
ऋणात्मक नहीं होने चाहिए और registers_size-1 से छोटे होने चाहिए.
|
A24 |
invoke-virtual और invoke-direct निर्देशों का method_id ऑपरेंड, किसी क्लास से जुड़ा होना चाहिए, न कि इंटरफ़ेस से. 037 वर्शन से पहले की Dex फ़ाइलों में,
invoke-super और
invoke-static निर्देशों के लिए भी यही बात लागू होनी चाहिए.
|
A25 |
invoke-virtual/range और
invoke-direct/range निर्देशों का method_id ऑपरेंड, किसी क्लास से जुड़ा होना चाहिए, न कि इंटरफ़ेस से. 037 वर्शन से पहले की Dex फ़ाइलों में,
invoke-super/range और
invoke-static/range निर्देशों के लिए भी यही बात लागू होनी चाहिए.
|
स्ट्रक्चरल बाइटकोड की सीमाएं
स्ट्रक्चरल कंस्ट्रेंट, बाइटकोड के कई एलिमेंट के बीच के संबंधों पर पाबंदियां होती हैं. आम तौर पर, कंट्रोल या डेटा-फ़्लो विश्लेषण की तकनीकों का इस्तेमाल किए बिना, इनकी जांच नहीं की जा सकती.
पहचानकर्ता | ब्यौरा |
---|---|
B1 | आर्ग्युमेंट (रजिस्टर और इमीडिएट वैल्यू) की संख्या और टाइप, हमेशा निर्देश से मेल खाने चाहिए. |
B2 | रजिस्टर किए गए पेयर को कभी अलग नहीं किया जाना चाहिए. |
B3 | किसी रजिस्टर (या पेयर) को पढ़ने से पहले, उसे असाइन करना होगा. |
B4 |
invoke-direct निर्देश में, सिर्फ़ मौजूदा क्लास या उसकी किसी एक सुपरक्लास में, किसी इंस्टेंस को शुरू करने वाले फ़ंक्शन या तरीके को शुरू करना चाहिए.
|
B5 | इंस्टेंस को शुरू करने वाले फ़ंक्शन को सिर्फ़ ऐसे इंस्टेंस पर शुरू किया जाना चाहिए जिसे शुरू नहीं किया गया है. |
B6 | इंस्टेंस के तरीकों को सिर्फ़ इंस्टेंस पर और इंस्टेंस फ़ील्ड को सिर्फ़ पहले से शुरू किए गए इंस्टेंस पर ऐक्सेस किया जा सकता है. |
B7 |
अगर किसी new-instance निर्देश को फिर से चलाया जाता है, तो उस रजिस्टर का इस्तेमाल नहीं किया जाना चाहिए जिसमें new-instance निर्देश का रिज़ल्ट सेव होता है. ऐसा तब किया जाना चाहिए, जब इंस्टेंस को शुरू करने से पहले ही new-instance निर्देश को फिर से चलाया जाता है.
|
B8 |
किसी इंस्टेंस के सदस्यों को ऐक्सेस करने से पहले, इंस्टेंस को शुरू करने वाले फ़ंक्शन को किसी दूसरे इंस्टेंस को शुरू करने वाले फ़ंक्शन (एक ही क्लास या सुपरक्लास) को कॉल करना होगा.
अपवाद, ऐसे इंस्टेंस फ़ील्ड होते हैं जिन्हें इनहेरिट नहीं किया जाता. इन्हें किसी दूसरे इनिशलाइज़र और आम तौर पर Object क्लास को कॉल करने से पहले असाइन किया जा सकता है.
|
B9 | सभी असली तरीके के आर्ग्युमेंट, उनके संबंधित औपचारिक आर्ग्युमेंट के साथ असाइनमेंट के मुताबिक होने चाहिए. |
B10 | हर इंस्टेंस मेथड को कॉल करने के लिए, असल इंस्टेंस, निर्देश में बताई गई क्लास या इंटरफ़ेस के साथ असाइनमेंट के लिहाज़ से काम का होना चाहिए. |
B11 |
return<kind> निर्देश, उसके तरीक़े के रिटर्न टाइप से मेल खाना चाहिए.
|
B12 | किसी सुपरक्लास के सुरक्षित मेंबर को ऐक्सेस करते समय, ऐक्सेस किए जा रहे इंस्टेंस का असल टाइप, मौजूदा क्लास या उसकी किसी सबक्लास का होना चाहिए. |
B13 | स्टैटिक फ़ील्ड में सेव की गई वैल्यू का टाइप, असाइनमेंट के साथ काम करने वाला या फ़ील्ड के टाइप में बदला जा सकने वाला होना चाहिए. |
B14 | किसी फ़ील्ड में सेव की गई वैल्यू का टाइप, फ़ील्ड के टाइप के साथ काम करने वाला या उसमें बदला जा सकने वाला होना चाहिए. |
B15 | ऐरे में सेव की गई हर वैल्यू का टाइप, ऐरे के कॉम्पोनेंट टाइप के साथ असाइनमेंट के लिहाज़ से काम करना चाहिए. |
B16 |
throw निर्देश का A ऑपरेंड,
असाइनमेंट के लिए java.lang.Throwable के साथ काम करना चाहिए.
|
B17 |
किसी तरीके का आखिरी निर्देश, बैकवर्ड
goto या शाखा, return या
throw निर्देश होना चाहिए. insns कलेक्शन को सबसे नीचे नहीं छोड़ा जा सकता.
|
B18 | किसी पुराने रजिस्टर पेयर का असाइन नहीं किया गया आधा हिस्सा तब तक नहीं पढ़ा जा सकता (इसे अमान्य माना जाता है), जब तक कि उसे किसी दूसरे निर्देश से फिर से असाइन नहीं किया जाता. |
B19 |
insns कलेक्शन में, move-result<kind> निर्देश के ठीक पहले invoke-<kind> निर्देश होना चाहिए. इसका एक अपवाद है
move-result-object निर्देश, जिसके पहले
filled-new-array निर्देश भी हो सकता है.
|
B20 |
move-result<kind> निर्देश के ठीक पहले, असल कंट्रोल फ़्लो में, मैच करने वाला return-<kind> निर्देश होना चाहिए. इसमें, निर्देश पर सीधे तौर पर जाने की ज़रूरत नहीं है. हालांकि, move-result-object
निर्देश के लिए ऐसा नहीं है. इसके लिए, पहले
filled-new-array निर्देश भी दिया जा सकता है.
|
B21 |
move-exception निर्देश, अपवाद हैंडलर में सिर्फ़ पहले निर्देश के तौर पर दिखना चाहिए.
|
B22 |
packed-switch-data , sparse-switch-data ,
और fill-array-data स्यूडो-निर्देशों को कंट्रोल फ़्लो से ऐक्सेस नहीं किया जा सकता.
|