د OpenVPN مرستندوی باینري په Android 10 کې ناکامېږي: اجازه رد شوه
Android 10 هغه مرستندوی فایل چلولو څخه انکار کوي چې اپلیکیشن په خپل ذخیره کې لیکلی وي۔ logcat ولولئ، مرستندوی د اصلي کتابخانې په توګه وسپارئ او د bundle جوړښتونه سم کړئ۔
اپلیکیشن په Android 9 کې کار کاوه او د Android 10 تازه کولو وروسته په هماغه تلیفون کې مري۔ ستاسو پروفایل نه دی لاس وهل شوی، سندونه هماغه دي، او ناورین له هرې تصدیق کولو ترافیک څخه مخکې راځي۔ logcat لومړی یو صفر اشاره کوونکی ښیي، او له هغه څو کرښې پورته دی Cannot run program ...: error=13, Permission denied۔ هغه پیغام د فایل چلولو په اړه دی، ستاسو د ترتیباتو لوستلو په اړه نه۔
تېروتنه 13 په رښتیا څه ردوي
Android 10، د API کچه 29، اپلیکیشنونه له دې څخه ودرول چې هغه فایلونه چې په خپل ډاټا فولډر کې یې لیکلي وو، چل کړي۔ قاعده هغه ذخیرې ته نیول کېږي چې لومړی د لیکلو وړ او بیا د چلولو وړ وي، او دا هغه څه دي چې له assets څخه کاپي کوونکی پیلوونکی جوړوي۔ د ics-openvpn هستې زاړه جوړښتونه په لومړي پیل کې له APK څخه د چلولو وړ openvpn فایل راوباسي او د ProcessBuilder له لارې یې پیلوي۔ ایستل لاهم بریالي کېږي؛ رد شوی چلول دي۔ هغه اپلیکیشن چې API 29 په نښه کوي، دا قاعده په میراث وړي حتی کله چې په هغه وسیله چې له زاړه خپریدو سره راغلې وي کار کوي، ځکه یو تازه کول کولی شي هغه جوړښت مات کړي چې چا ته یې لاس نه دی ورکړی۔
په ردولو کې د یو فولډر نوم لپاره ځانګړی څه نشته۔ هغه فایل چې اپلیکیشن د خپل ډاټا فولډر لاندې جوړ کړی، د لارې په پام کې نه نیولو سره د نه چلېدونکي په توګه ګڼل کېږي، نو getFilesDir(), getCacheDir() او یو ځانګړی فرعي فولډر ټول په یوه طریقه ناکامېږي۔
د مرستندوی ناورین له پروفایل ستونزې څخه بېل کړئ
د پورتنۍ برخې سکرول کولو پرځای د پروسې د پیل شاوخوا لاګ ولولئ۔ هغه لاسلیک چې باید ومومئ کرښه ده error=13، او له هغې پورته سټک ټریس معمولا د هغه پیلوونکي میتود نوم اخلي چې ProcessBuilder یې غوښتلی:
adb logcat -d | grep -n -i -E "cannot run program|permission denied|startOpenVPN"که مرستندوی هیڅکله نه وي پیل شوی، تاسو به د OpenVPN لاګ هیڅ عاید ونه ګورئ: نه د کوډ خبرې اترې، نه لېږل شوې لارې، نه د DNS ترتیبات۔ که هغه کرښې ښکارېدلې او ناکامي وروسته راغله، باینري چل شوی او ستونزه په پروفایل، سرور یا د لارښوونې په پوړ کې ده۔ همدا یوه توپیر .ovpn فایلونو ایډیټ کولو ته تلونکی ډیر وخت ژغوري چې هیڅکله مجرم نه وو۔ دا هم درته وایي چې لاندې دوه سمونو کې کوم یو واقعا ته ته اړتیا لرې۔
هغه وسیله چې تاسو یې ازموئ د هغې API کچه هم وګورئ، ستاسو د جوړښت ترتیباتو کې هغه نه۔ په API 28 کې د امولیټر عکس هیڅ شی بیا نه جوړوي، ځکه محدودیت یوازې له 29 پورته چیچل کوي۔ په هماغه وخت کې په خپل جوړښت فایل کې هدف SDK وګورئ: همدا لوړول یې دا قاعده دننه راکاږي۔
adb shell getprop ro.build.version.sdkولې باینري بل ځای کاپي کول مرسته نه کوي
ښکاره لار، مرستندوی په بله د لیکلو وړ فولډر کې لیکل، د هماغه دلیل له امله ناکامېږي چې اصلي ناکام شو۔ Android لا هم اجازه ورکوي چې په اپلیکیشن د اصلي کتابخانو فولډر کې نصب شوې شریکې کتابخانې چل شي، ځکه نصبونکی یې بسته بندي کوي، نه دا چې د چلېدو په وخت کې لیکل کېږي۔ هماغه فولډر یوازینی ځای دی چې پیلوونکی باید ورته اشاره وکړي۔ هر هغه څه چې تاسو یې په خپله د چلېدو په وخت کې وباسئ، هر نوم چې ورته ورکړئ، په رد شوې کټګورۍ کې پاتې کېږي۔
بهرنۍ ذخیره لا بدتره ده: دا له noexec سره نښلول شوې، او هلته ایښودل شوی مرستندوی هیڅ اپلیکیشن نشي پیلولی۔ د اپلیکیشن ډاټا پاکول هم زاړه چلند نه راګرځوي، ځکه بل ځل چلول یوازې هماغه نه چلېدونکې کاپي بیا جوړوي۔
پیلوونکی بسته بندي شوې کتابخانې ته وګرځوئ
د مرستندوی نوم د شریکې کتابخانې نوم ته بدل کړئ او د هغه هر ABI لپاره چې ملاتړ یې کوئ jniLibs لاندې یې وسپارئ، بیا پیلوونکی له API 28 وروسته د نصب شوې کتابخانې لار بیرته راکړي:
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
return new File(context.getApplicationInfo().nativeLibraryDir,
"libovpnexec.so").getPath();
}کتابخانه باید د نصب په وخت کې وایستل شي ترڅو هغه لار ریښتینی فایل ولري، نو android:extractNativeLibs="true" دې <application> عنصر ته وټاکئ۔ که manifest یوځای کوونکی بل ارزښت راوړي، د هغه ترڅنګ tools:replace="android:extractNativeLibs" اضافه کړئ۔ د application عنصر حواله بیانوي چې دا ځانګړتیا څه کنټرولوي۔
کله چې پیلوونکی په لاس پاچ کوئ، له دوه ځله شوې سیمه ییزې بدلېدونکې څخه ډډه وکړئ۔ زاړه سرچینې په هماغه میتود کې وروسته nativeAPI اعلانوي، او دوهم اعلان د چلېدو نه بلکه د کمپایل تېروتنه ده، نو جوړښت ژر ناکامېږي او تېروتنه اسانه لیدل کېږي۔ په Gradle بلاک کې د ABI لیست له هغو فولډرونو سره سم وساتئ چې اضافه یې کوئ۔
د خپریدو محصول له ازموینې جوړښت سره سم کړئ
د ډیبګ APK کولی شي تونل پورته کړي پداسې حال کې چې د خپریدو bundle لا هم ناورین کوي، ځکه bundle اصلي کتابخانې په بله بڼه بسته بندي کوي او کولی شي له ارشیف څخه یې فشار شوي وړاندې کړي۔ که یوازې له bundle څخه راغلي جوړښتونه ناکامېږي، دا gradle.properties ته اضافه کړئ او بیا جوړ کړئ:
android.bundle.enableUncompressedNativeLibs=falseبیا ډاډ ترلاسه کړئ چې نصب شوې بسته هغه ABI راپور ورکوي چې تاسو یې تمه لرئ، او که دواړه سپارئ، په 32-بټ او 64-بټ وسیله کې ازموینه تکرار کړئ۔ د بستې مدیر خپله ټاکل شوې ABI نوموي، نو هغه وسیله چې 32 بټ ته بیرته لوېدلې ده دلته ښکاري نه په ناورین راپور کې:
adb shell dumpsys package com.example.openvpn | grep -i primaryCpuAbiد یو ABI لپاره ورکه کتابخانه د اصلې اجازې تېروتنه یوازې په هماغه وسیله بیا جوړوي، ځکه یو بریالی ازموینه تلیفون ثبوت نه دی۔ د manifest بیرغ، د کتابخانې نوم او د bundle ترتیبات یوځای وسپارئ؛ یو بدل او نور هیر کړئ نو بیرته هماغه ناورین ته ورګرځئ۔ پایډ حل دا دی چې د پیچ تل پاتې کولو پرځای ساتل شوې هستې خپریدو ته لاړ شئ۔