Windows - Phones - Visionen
[Hack] Linken von nativen Bibliotheken - Druckversion

+- Windows - Phones - Visionen (https://www.wpvision.de)
+-- Forum: Software | Hardware (https://www.wpvision.de/forumdisplay.php?fid=6)
+--- Forum: Windows Allgemein (https://www.wpvision.de/forumdisplay.php?fid=207)
+---- Forum: Entwicklerbereich (https://www.wpvision.de/forumdisplay.php?fid=177)
+----- Forum: StarGate01 (https://www.wpvision.de/forumdisplay.php?fid=189)
+----- Thema: [Hack] Linken von nativen Bibliotheken (/showthread.php?tid=7727)



[Hack] Linken von nativen Bibliotheken - StarGate01 - 19.10.16

Hallo liebe Forengemeinde,

Zunächst: Das ist ein Hack. D.h. ich übernehme [B]keine Garantie dass es klappt, und ich übernehme auch [B]keine Haftung für eventuell entstandene Schäden.
Außerdem hab ich diese Methode weder erfunden, noch den ganzen Code selbst geschrieben. Quellen stehen unten.
[/B][/B]

Die Anleitung ist für Programmierer mit Genunlocken WP8 oder WP8.1 (WP10 ungetestet) Handys.

Schon einmal habe ich eine Möglichkeit vorgestellt aus interop-geunlockten Apps heraus native Bibliotheken aufzurufen: http://wpvision.de/stargate01/6644-%5Bhack%5D-aufrufen-von-nativen-bibliotheken.html
Diese Methode ist aber relativ komplex und benötigt viel Code.

Nun stelle ich eine etwas leichtere Methode vor, die darauf basiert den Linker richtig zu konfigurieren, sodass nicht die Bibliothek erst zur Laufzeit dynamisch geladen werden muss, sondern vom Loader automatisch geladen wird.
Zunächst muss die spezielle Bibliothek aus dem Handy extrahiert werden, dafür greift man mittels den Full-FS-Access-Hacks auf C:\Windows\system32 zu und kopiert die entsprechende dll-Datei auf den PC.
Dann nutzt man die Visual-Studio-Tools (VS muss also installiert sein) um aus der dll eine lib-Datei mit den extrahierten Methodeneinstiegspunkten zu kompilieren. Dazu habe ich auch ein kleines Batch-Skript geschrieben:

Batch Code (0_dlltolib.bat)
Code:
@echo off
set ofile=%~f1
echo Processing %ofile%
set odir=%~d1%~p1
set tdir=%odir%tmp
echo Creating tmp dir
mkdir "%tdir%"
echo Loading VS tools
pushd "C:\Program Files (x86)\Microsoft Visual Studio 12.0\VC"
call vcvarsall.bat x86_arm
echo Dumping exports
dumpbin /exports "%ofile%" > "%tdir%\%~n1.dpb"
echo Writing def header
echo LIBRARY %~n1 > "%tdir%\%~n1.def"
echo EXPORTS >> "%tdir%\%~n1.def"
echo Writing exports to def
set infile="%tdir%\%~n1.dpb"
for /f "skip=19 tokens=4" %%A in ('type %infile%') do echo %%A >> "%tdir%\%~n1.def"
echo Compiling lib
lib /def:"%tdir%\%~n1.def" /out:"%odir%\%~n1.lib" /machine:ARM
echo Removing tmp dir
rd /s /q "%tdir%"
popd
pause

So muss die dll-Datei nur noch auf die Batch-Datei gezogen werden.
Der Pfad C:\Program Files (x86)\Microsoft Visual Studio 12.0\VC muss eventuell angepasst werden.
Es ist sinnvoll, alle so produzierten lib-Dateien in einem Ordner aufzubewahren, dazu später mehr.

In Visual Studio fügt man seiner (Silverlight) App dann eine sog. Komponente für Windows-Runtime (Silverlight) hinzu.
In den Eigenschaften dieser ändert man folgende Felder bei der Einstellung des Linkers:
  • Allgemein->Zusätzliche Bibliotheksverzeichnisse: Der obengenannte Ordner
  • Eingabe->Zusätzliche Abhängigkeiten: Die Namen der erforderlichen lib-Dateien
Nun muss noch eine C++-Header Datei angelegt werden, die die Methodensignaturen in WinAPI-Stil enthält.
Diese kann dann (mit extern "C") inkludiert werden.

Nun also ein kleines Beispiel zur besseren Verdeutlichung:
Man will die Methode ShellChromeAPI.dll#Shell_TurnScreenOn aufrufen.
Dann wird der Linker entspechend konfiguriert für die Datei ShellChromeApi.lib und das entsprechende Verzeichnis.
Die Methodensignatur errät man oder ermittelt sie mit Hilfe eines Decompilers in mühevoller Arbeit:

C Code (ShellChromeApi.h)
Code:
#pragma once
HRESULT Shell_TurnScreenOn(BOOL bOn);

Diese Datei kann dann eingebunden werden:

C++ Code (NativeComponent.h)
Code:
#pragma once


using namespace Platform;


namespace NativeComponent
{


    public ref class ShellChromeAPI sealed
    {


    public:
        ShellChromeAPI();
        void TurnScreenOn(bool state);


    };


}

C++ Code (NativeComponent.cpp)
Code:
#include "pch.h"
#include "Native.h"


extern "C"
{
    #include "ShellChromeAPI.h"
}


using namespace std;
using namespace Platform;
using namespace NativeComponent;




ShellChromeAPI::ShellChromeAPI()
{


}


void ShellChromeAPI::TurnScreenOn(bool state)
{
    Shell_TurnScreenOn(state);
}

Nach dem Kompilieren und verknüpfen kann die Komponente von C# aus genutzt werden:

C# Code
Code:
using NativeComponent;
ShellChromeAPI api = new ShellChromeAPI();
api.TurnScreenOn(false);

In Aktion seht ihr diese Strategie schon bald bei meinem momentanen Projekt, http://wpvision.de/windows-phone-hacking/6770-%5Bhack%5D-midnight-lockscreen-lockscreen-app-und-bibliothek-open-source.html .
Ich hoffe diese Anleitung hat dem ein oder anderem geholfen und vielleicht sogar Lust gemacht selbt aktiv zu werden.

Quellen:
http://wpvision.de/stargate01/6644-%5Bhack%5D-aufrufen-von-nativen-bibliotheken.html
https://www.hex-rays.com/products/ida/index.shtml
https://adrianhenke.wordpress.com/2008/12/05/create-lib-file-from-dll/
c++ - How to make a .lib file when have a .dll file and a header file - Stack Overflow
https://github.com/imReker/rkNativeLib
https://github.com/gebucholz/Phate