Giter VIP home page Giter VIP logo

enjarify's Introduction

Introduction

Enjarify is a tool for translating Dalvik bytecode to equivalent Java bytecode. This allows Java analysis tools to analyze Android applications.

Usage and installation

Enjarify is a pure python 3 application, so you can just git clone and run it. To run it directly, assuming you are in the top directory of the repository, you can just do

python3 -O -m enjarify.main yourapp.apk

For normal use, you'll probably want to use the wrapper scripts and set it up on your path.

Linux

For convenience, a wrapper shell script is provided, enjarify.sh. This will try to use Pypy if available, since it is faster than CPython. If you want to be able to call Enjarify from anywhere, you can create a symlink from somewhere on your PATH, such as ~/bin. To do this, assuming you are inside the top level of the repository,

ln -s "$PWD/enjarify.sh" ~/bin/enjarify

Windows

A wrapper batch script, enjarify.bat, is provided. To be able to call it from anywhere, just add the root directory of the repository to your PATH. The batch script will always invoke python3 as interpreter. If you want to use pypy, just edit the script.

Usage

Assuming you set up the script on your path correctly, you can call it from anywhere by just typing enjarify, e.g.

enjarify yourapp.apk

The most basic form of usage is to just specify an apk file or dex file as input. If you specify a multidex apk, Enjarify will automatically translate all of the dex files and output the results in a single combined jar. If you specify a dex file, only that dex file will be translated. E.g. assuming you manually extracted the dex files you could do

enjarify classes2.dex

The default output file is [inputname]-enjarify.jar in the current directory. To specify the filename for the output explicitly, pass the -o or --output option.

enjarify yourapp.apk -o yourapp.jar

By default, Enjarify will refuse to overwrite the output file if it already exists. To overwrite the output, pass the -f or --force option.

Why not dex2jar?

Dex2jar is an older tool that also tries to translate Dalvik to Java bytecode. It works reasonably well most of the time, but a lot of obscure features or edge cases will cause it to fail or even silently produce incorrect results. By contrast, Enjarify is designed to work in as many cases as possible, even for code where Dex2jar would fail. Among other things, Enjarify correctly handles unicode class names, constants used as multiple types, implicit casts, exception handlers jumping into normal control flow, classes that reference too many constants, very long methods, exception handlers after a catchall handler, and static initial values of the wrong type.

Limitations

Currently, only version 35 dex files are supported. This means that the Java 8 related bytecode features introduced in Android N, O, and P are not supported.

Enjarify does not currently translate optional metadata such as sourcefile attributes, line numbers, and annotations.

Enjarify tries hard to successfully translate as many classes as possible, but there are some potential cases where it is simply not possible due to limitations in Android, Java, or both. Luckily, this only happens in contrived circumstances, so it shouldn't be a problem in practice.

Performance tips

PyPy is much faster than CPython. To install PyPy, see http://pypy.org/. Make sure you get PyPy3 rather than regular PyPy. The Linux wrapper script will automatically use the command pypy3 if available. On Windows, you'll need to edit the wrapper script yourself.

By default, Enjarify runs optimizations on the bytecode which make it more readable for humans (copy propagation, unused value removal, etc.). If you don't need this, you can speed things up by disabling the optimizations with the --fast option. Note that in the very rare case where a class is too big to fit in a classfile without optimization, Enjarify will automatically retry it with all optimizations enabled, so this option does not affect the number of classes that are successfully translated.

Disclaimer

This is not an official Google product (experimental or otherwise), it is just code that happens to be owned by Google.

enjarify's People

Contributors

ajinabraham avatar arctangent1759 avatar jjqq2013 avatar keszybz avatar reinerh avatar storyyeller avatar torunr avatar virb3 avatar yurushao avatar zyv avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

enjarify's Issues

58057 classes translated successfully, 1 classes had errors

First time I used the tool on macOS with M1 chips (ARM) on Python 3.9.5.

I got this Traceback for the SymbolTableHolder, where this specific class decompile well with jadx

58000 classes processed
Output written to com.myapp.android-enjarify.jar
com/myapp/android/symbols/SymbolTableHolder$GeneratedSymbolTable.class Traceback (most recent call last):
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/constantpool.py", line 46, in _get
    return d[args]
KeyError: 65534

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/writeclass.py", line 116, in toClassFile
    pool, rest_stream = classFileAfterPool(cls, opts=opts)
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/writeclass.py", line 100, in classFileAfterPool
    writeMethods(pool, stream, cls.data.methods, opts=opts)
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/writeclass.py", line 64, in writeMethods
    code_irs.append(writebytecode.getCodeIR(pool, method, opts=opts))
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/writebytecode.py", line 21, in getCodeIR
    irdata = writeir.writeBytecode(pool, method, opts)
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/writeir.py", line 598, in writeBytecode
    VISIT_FUNCS[instr.type](method, dex, instr_d, type_data, block, instr)
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/writeir.py", line 310, in visitConstString
    block.ldc(block.pool.string(val))
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/constantpool.py", line 80, in string
    def string(self, s): return self._get(CONSTANT_String, self.utf8(s))
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/constantpool.py", line 49, in _get
    d[args] = index = self._getInd(low, _width(tag))
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/constantpool.py", line 127, in _getInd
    raise error.ClassfileLimitExceeded()
enjarify.jvm.error.ClassfileLimitExceeded

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/constantpool.py", line 46, in _get
    return d[args]
KeyError: b'createSymbolTable'

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/main.py", line 38, in translate
    class_data = writeclass.toClassFile(cls, opts)
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/writeclass.py", line 119, in toClassFile
    pool, rest_stream = classFileAfterPool(cls, opts=options.ALL)
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/writeclass.py", line 100, in classFileAfterPool
    writeMethods(pool, stream, cls.data.methods, opts=opts)
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/writeclass.py", line 69, in writeMethods
    writeMethod(pool, stream, method, code_attrs.get(method))
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/writeclass.py", line 49, in writeMethod
    stream.u16(pool.utf8(method.id.name))
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/constantpool.py", line 77, in utf8
    return self._get(CONSTANT_Utf8, s)
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/constantpool.py", line 49, in _get
    d[args] = index = self._getInd(low, _width(tag))
  File "/Users/ebauger/Documents/src_app/enjarify/enjarify/jvm/constantpool.py", line 172, in _getInd
    raise error.ClassfileLimitExceeded()
enjarify.jvm.error.ClassfileLimitExceeded

58057 classes translated successfully, 1 classes had errors

Great work btw!

TypeError: object of type 'NoneType' has no len()

I got the following errors:

File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/e/c/e.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/e/f/a.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/e/f/b.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/e/f/ba.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/e/f/c.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/e/f/f.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/e/l/a/g.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/e/l/a/h.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/e/l/a/i.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/e/l/b/h.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/e/l/b/i.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/e/l/b/j.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/b/a/a/d.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/b/a/c.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/b/a/g.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/b/a/i.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/b/a/j.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/b/a/k.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/b/a/n.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/b/d/a.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/b/d/a/a.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/b/d/a/c.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/b/d/c.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/b/f/ah.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/d/a/e.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/d/a/i.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/d/a/n.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

org/a/s/d/a/s.class Traceback (most recent call last):
File "/mnt/sda4/project/android/enjarify/enjarify/main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/writeclass.py", line 122, in toClassFile
pool.write(stream)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 135, in write
self._writeEntry(stream, item)
File "/mnt/sda4/project/android/enjarify/enjarify/jvm/constantpool.py", line 104, in _writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

Allow relative path for APK file

Currently on Windows, enjarify foo.apk or enjarify .\foo.apk won't work; enjarify \full\path\to\foo.apk works. Is this expected?

a little confused about the location the classes generated

I just found that the inner .class generated by enjarify is not in its original dir? is it possible to just generate it in the default dir? or could you please give me some explaination so that I could do it by myself since I am also using apktool(It works like that.)for example
here is the enjarify result

Mode                LastWriteTime         Length Name
----                -------------         ------ ----
d-----         2017/7/5     11:10                air
d-----         2017/7/5     11:10                atast
-a----         2017/7/5     11:10            452 AppEntry$1.class

where the following is the result of apktool in the dir atast

Mode                LastWriteTime         Length Name
----                -------------         ------ ----
-a----         2017/7/5     11:10           1366 AppEntry$1.smali
-a----         2017/7/5     11:10           1124 AppEntry$2.smali
-a----         2017/7/5     11:10           1094 AppEntry$3.smali
-a----         2017/7/5     11:10           2318 AppEntry$4.smali
-a----         2017/7/5     11:10         110804 AppEntry.smali
-a----         2017/7/5     11:10            668 GetVersionCode.smali
-a----         2017/7/5     11:10            509 R$attr.smali
-a----         2017/7/5     11:10            586 R$drawable.smali
-a----         2017/7/5     11:10            694 R$raw.smali
-a----         2017/7/5     11:10            758 R$string.smali
-a----         2017/7/5     11:10            590 R$style.smali
-a----         2017/7/5     11:10            549 R.smali

thanks a lot.

An exception occurs when the library containing Zxing is compiled

Microsoft Windows [版本 6.1.7601]
版权所有 (c) 2009 Microsoft Corporation。保留所有权利。

C:\Users\amin>enjarify D:\QcUsers\Win7\Administrator\Desktop\Fordeal.apk -
o D:\QcUsers\Win7\Administrator\Desktop\FORDEAL.jar
1000 classes processed
2000 classes processed
3000 classes processed
4000 classes processed
5000 classes processed
6000 classes processed
7000 classes processed
8000 classes processed
9000 classes processed
Output written to D:\QcUsers\Win7\Administrator\Desktop\FORDEAL.jar
com/google/zxing/aztec/b/d.class Traceback (most recent call last):
File "F:\PythonProjects\enjarify\enjarify\main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "F:\PythonProjects\enjarify\enjarify\jvm\writeclass.py", line 122, in toC
lassFile
pool.write(stream)
File "F:\PythonProjects\enjarify\enjarify\jvm\constantpool.py", line 135, in w
rite
self._writeEntry(stream, item)
File "F:\PythonProjects\enjarify\enjarify\jvm\constantpool.py", line 104, in _
writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

com/google/zxing/common/i.class Traceback (most recent call last):
File "F:\PythonProjects\enjarify\enjarify\main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "F:\PythonProjects\enjarify\enjarify\jvm\writeclass.py", line 122, in toC
lassFile
pool.write(stream)
File "F:\PythonProjects\enjarify\enjarify\jvm\constantpool.py", line 135, in w
rite
self._writeEntry(stream, item)
File "F:\PythonProjects\enjarify\enjarify\jvm\constantpool.py", line 104, in _
writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

com/google/zxing/pdf417/d.class Traceback (most recent call last):
File "F:\PythonProjects\enjarify\enjarify\main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "F:\PythonProjects\enjarify\enjarify\jvm\writeclass.py", line 122, in toC
lassFile
pool.write(stream)
File "F:\PythonProjects\enjarify\enjarify\jvm\constantpool.py", line 135, in w
rite
self._writeEntry(stream, item)
File "F:\PythonProjects\enjarify\enjarify\jvm\constantpool.py", line 104, in _
writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

com/google/zxing/pdf417/decoder/h.class Traceback (most recent call last):
File "F:\PythonProjects\enjarify\enjarify\main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "F:\PythonProjects\enjarify\enjarify\jvm\writeclass.py", line 122, in toC
lassFile
pool.write(stream)
File "F:\PythonProjects\enjarify\enjarify\jvm\constantpool.py", line 135, in w
rite
self._writeEntry(stream, item)
File "F:\PythonProjects\enjarify\enjarify\jvm\constantpool.py", line 104, in _
writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

com/google/zxing/pdf417/encoder/a.class Traceback (most recent call last):
File "F:\PythonProjects\enjarify\enjarify\main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "F:\PythonProjects\enjarify\enjarify\jvm\writeclass.py", line 122, in toC
lassFile
pool.write(stream)
File "F:\PythonProjects\enjarify\enjarify\jvm\constantpool.py", line 135, in w
rite
self._writeEntry(stream, item)
File "F:\PythonProjects\enjarify\enjarify\jvm\constantpool.py", line 104, in _
writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

com/google/zxing/qrcode/a/b.class Traceback (most recent call last):
File "F:\PythonProjects\enjarify\enjarify\main.py", line 38, in translate
class_data = writeclass.toClassFile(cls, opts)
File "F:\PythonProjects\enjarify\enjarify\jvm\writeclass.py", line 122, in toC
lassFile
pool.write(stream)
File "F:\PythonProjects\enjarify\enjarify\jvm\constantpool.py", line 135, in w
rite
self._writeEntry(stream, item)
File "F:\PythonProjects\enjarify\enjarify\jvm\constantpool.py", line 104, in _
writeEntry
stream.u16(len(val))
TypeError: object of type 'NoneType' has no len()

9498 classes translated successfully, 6 classes had errors

C:\Users\amin>

Featurte request: Line numbers etc.

Optional metadata like source file attributes, line numbers and annotations are currently not translated.

All of this would be really useful for debugging/reverse engineering apps... Would it be hard to add?

Improve installation process

Any particular reason why this isn't available on PyPI/installable via pip? Given that this package doesn't have any particularly-difficult install steps, a simple setup.py script should be just fine, combined with publishing it to PyPI.

Add Dockerfile to repo

Add Dockerfile to allow easy building of container that contain enjairfy from git repo, which use COPY . instruction and .dockerignore file if needed.

Currently I use (which do git clone inside the container):

FROM python:3
RUN set -ex; \
    git clone --depth 1 https://github.com/Storyyeller/enjarify/; \
    ln -s /enjarify/enjarify.sh /usr/local/bin/enjarify;
WORKDIR /enjarify/
ENTRYPOINT ["python3", "-O", "-m", "enjarify.main"]
CMD ["--help"]

build:

docker run --rm -t enjarify .

run example:

docker run --rm -ti --network none -v /host/dex-files/:/f/:ro -v /host/jar-from-dex/:/o/:rw --entrypoint /bin/bash enjarify

tests fail with python 3.9

+ /usr/bin/python3 -m enjarify.runtests
Traceback (most recent call last):
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writeclass.py", line 116, in toClassFile
    pool, rest_stream = classFileAfterPool(cls, opts=opts)
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writeclass.py", line 100, in classFileAfterPool
    writeMethods(pool, stream, cls.data.methods, opts=opts)
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writeclass.py", line 65, in writeMethods
    code_attrs = writebytecode.finishCodeAttrs(pool, code_irs, opts=opts)
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writebytecode.py", line 75, in finishCodeAttrs
    return {irdata.method: writeCodeAttributeTail(pool, irdata, opts=opts) for irdata in code_irs}
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writebytecode.py", line 75, in <dictcomp>
    return {irdata.method: writeCodeAttributeTail(pool, irdata, opts=opts) for irdata in code_irs}
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writebytecode.py", line 99, in writeCodeAttributeTail
    raise error.ClassfileLimitExceeded()
enjarify.jvm.error.ClassfileLimitExceeded

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/usr/lib64/python3.9/runpy.py", line 197, in _run_module_as_main
    return _run_code(code, main_globals, None,
  File "/usr/lib64/python3.9/runpy.py", line 87, in _run_code
    exec(code, run_globals)
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/runtests.py", line 45, in <module>
    executeTest('test{}'.format(i), opts)
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/runtests.py", line 30, in executeTest
    classes, errors = translate(rawdex, opts=opts, allowErrors=False)
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/main.py", line 38, in translate
    class_data = writeclass.toClassFile(cls, opts)
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writeclass.py", line 119, in toClassFile
    pool, rest_stream = classFileAfterPool(cls, opts=options.ALL)
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writeclass.py", line 100, in classFileAfterPool
    writeMethods(pool, stream, cls.data.methods, opts=opts)
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writeclass.py", line 64, in writeMethods
    code_irs.append(writebytecode.getCodeIR(pool, method, opts=opts))
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writebytecode.py", line 21, in getCodeIR
    irdata = writeir.writeBytecode(pool, method, opts)
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writeir.py", line 597, in writeBytecode
    VISIT_FUNCS[instr.type](method, dex, instr_d, type_data, block, instr)
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writeir.py", line 380, in visitFillArrayData
    block.fillarraydata(_arrStoreOps.get(elet, AASTORE), st, arrdata)
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writeir.py", line 146, in fillarraydata
    self.fillarraysub(op, [partial(self.const, val, stype) for val in vals])
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writeir.py", line 129, in fillarraysub
    cb()
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/writeir.py", line 118, in const
    self.add(ir.PrimConstant(stype, val, pool=pool))
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/ir.py", line 82, in __init__
    self.bytecode = calc.calc(st, val)
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/constants/calc.py", line 179, in calc
    return calcDouble(val)
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/constants/calc.py", line 162, in calcDouble
    def calcDouble(x): return _calcDouble(normalizeDouble(x))
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/constants/calc.py", line 157, in _calcDouble
    return _calcLong(mantissa) + bytes([L2D]) + exponent_parts
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/constants/calc.py", line 66, in _calcLong
    result += _calcInt(low) + bytes([I2L, LXOR])
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/constants/calc.py", line 50, in _calcInt
    return _calcInt(high) + _calcInt(16) + bytes([ISHL]) + _calcInt(low) + bytes([IXOR])
  File "/var/tmp/enjarify/enjarify-1.0.3/enjarify/jvm/constants/calc.py", line 47, in _calcInt
    assert high
AssertionError

This is in Fedora rawhide with java-11-openjdk-headless-11.0.8.10-1.fc33.x86_64.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.