2016-04-02 6 views
1

私が入っているクラスでは、単純なmipsシミュレータに割り当てられています。私のプログラムが処理するはずの命令はバイナリファイルで与えられます。私はそのファイルから何かを使用する方法を知りません。ここに私のコードです:ファイルからバイナリデータをバイナリデータをバイナリ形式の2つのバイナリをPythonでどのように変換できますか?

import struct 
import argparse 

'''open a parser to get command line arguments ''' 
parser = argparse.ArgumentParser(description='Mips instruction simulator') 

'''add two required arguments for the input file and the output file''' 
parser.add_argument('-i', action="store", dest='infile_name', help="-i INPUT_FILE", required=True) 
parser.add_argument('-o', action="store", dest='outfile_name', help="-o OUTPUT_FILE_NAME", required=True) 

'''get the passed arguments''' 
args = parser.parse_args() 


class Disassembler: 
    '''Disassembler for mips code''' 
    instruction_buffer = None 
    instructions_read = 0 

    def __init__(self, filename): 
     bin_file = None 
     try: 
      bin_file = open(filename, 'rb') 
     except: 
      print("Input file: ", filename, " could not be opened. Check the name, permissions, or path") 
      quit() 

     while True: 
      read_bytes = bin_file.read(4) 
      if (read_bytes == b''): 
       break 
      int_var = struct.unpack('>I', read_bytes) 
      print(int_var) 

     bin_file.close() 


disembler = Disassembler(args.infile_name) 

私は4バイトを印刷しました。返されたものを見ました。 私は普通のビット(1と0だけ)を見ることを望んでいました。私が得たものは、私が読んだものからバイトストリングでした。だから、私はこれについて何ができるのかを知ろうと試みた。だから私は整数にこれらのバイト文字列を変換するために構造体を使用できることがわかった。それは(4294967295、)のような形式でそれらを出力します。

私はそれを使用可能な整数にするためにトリムしなければならないので、これはまだ厄介です。それでもそれをビット(ベース2)に変換する必要があります。入力ファイルの入力の半分が符号付き32ビット数であるため、構造体を使用してバイトを符号付きまたは符号なしとして読み取ることができます。

これはすべてバイナリファイルからビットを取得するよりも複雑なようです。これを行う簡単な方法はありますか?また、秘密のpythonコードに信じられないほど精通しておらず、バイナリデータを初めて使う人のように説明できますか?

私の全体的な目標は、読んだ4バイトのうち32ビットを真っ直ぐにすることです。ファイルの先頭はmipsオペコードのリストです。だから私は、これらの数字の特定の部分を見ることができるようにする必要があります、最初の5ビットのように、次の6、など。ファイルの最後には32ビットの符号付き整数値が含まれています。ファイルの2つの半分はブレークオペコードで区切られています。

私に教えていただきありがとうございます。それは私が捜索を通してどんなまっすぐな答えも見つけることができないことを私に夢中にさせている。バイナリファイルを見たい場合は、どこに、私はそれを投稿しますか教えてください。

+0

値のビットを[視覚化]したいだけですか(https://stackoverflow.com/questions/18111488/convert-integer-to-binary-in-python-and-compare-the-bits)またはそれらを[整数](https:// stackoverflow。com/questions/30971079/i-convert-an-to-a-bit-in-python)のフォームを使用してさらに操作できますか? – Reti43

+0

私は思ったようにそれらを読む必要があります。私はそれぞれの32ビット値の中から特定の長さが必要だからです。私は最初の6ビットが何か、次に次の5ビットなどを見なければならないように、私は考えるストレートビットの値が必要です。それについてもっと良い方法があるのではなく、私の知る限りでは、これが私がデータを扱う方法を知っている唯一の方法です。 – Jacob

+0

これを行うにはいくつかの方法があります。私のコメントの上のリンクを見てください。あなたの目標が何であるかを正確に質問することをお勧めします。そうでなければ、あなたが問題に取り入れようとしている解決策をより良い方法で提案することはできません。 – Reti43

答えて

1

ベア。これは、符号付き整数をビット列に変換したいときに迷惑になる可能性があります。 4バイトの変換ブロックを符号なし整数に

n = struct.unpack('>I', read_bytes)[0] 

を使用して、あなたはビットを印刷したい場合はビット列にそれを変換するformat(n, '032b')または'{0:032b}'.format(n)のいずれかを使用して:私はあなたが現在やっていることに固執することをお勧めします。整数のビットをアクセスしたり変更するには

、あなたは文字列変換を悩ますべきではありません、代わりにあなたはPythonのビット単位の演算子を使用する必要があり、&|^<<>>~。例:(n >> 7) & 1は、nのビット7を示します。

これらの演算子の詳細については、Unary arithmetic and bitwise operations以降のPythonドキュメントのセクションを参照してください。

+0

そこには何がありますか?私が構造体から戻ってくるのは、数字のための "(2370044120、)"です。私はちょうどそれをそのままフォーマットに渡すことはできますか?また、どのようにPythonのビットごとの演算子が動作するのですか? >>シフトは正しいですか? &1は何をするのですか?ビット演算子はstructから返されるもので動作しますか? – Jacob

+0

申し訳ありません、@ Jacob、 'struct.unpack'は常にタプルを返します。私は 'n'がPythonの整数になるようにコードを修正しました。また、 ''> I' 'フォーマット指定によって、符号なし32ビット数であることが保証されています。 –

+0

@Jacob:はい、 '>>'は右シフト、 '&'はビット単位のANDなので、 'c = a&b'は整数aとbの対応するビットに対してAND演算を行い、結果は「c」の対応するビットになる。従って、「n&1」は「n」の最下位ビットを評価する。 Pythonのビット演算子は、Cや他の多くの言語と非常によく似ています(Pythonの整数には固定ビット幅がないことを除けば)。逆アセンブラーを作っているのなら、ビットごとの演算子に精通していると思っていました。 :) –

0

この方法で、ファイルの各ビットにアクセスできます。例えば

"".join(format(i, "08b") for i in byte_string) 

:彼らは、彼らがする必要があるとして大だ:通常のPythonの整数は、固定ビット幅を持っていないことを念頭に置い

>>> "".join(format(i, "08b") for i in b"\x23\x54a") 
'001000110101010001100001' 
+0

'bin'は、結果として得られる文字列の長さを制御することはできません。また、あなたのコードと同じように、通常はスライスしたい' '0b ''を前に付けます。両方のカウントで 'format'関数またはメソッドが優れています。例えば、 'format(n、 '032b')' –

+0

これは他の質問で投稿されています。私がそれを使用することを躊躇する唯一の理由は、私はそれがどのように機能するのか分かりません。したがって、joinは、空の文字列にそのすべてを追加します。 bin(i)は数値をバイナリに変換するので、[2:]は接頭辞0bを取り除きますか?私はそれが十分にまっすぐな前進だと思っていますが、なぜそれの隣にb "\ x23 \ x53a"のiがありますか? bin関数の隣にforループを置くと、何ができますか?どのループがループしていますか?各バイト? – Jacob

+0

@ PM2Ringありがとう。私は各バイトが8ビットであるので '08b'に変更しました。毎回4バイトをintに変換する必要はありません。 – Bharel

関連する問題