disasm6502/lib.rs
1//! [Disasm6502](https://github.com/kondrak/disasm6502) - a 6502 disassembler crate.
2//!
3//! A crate providing functionality to disassemble 6502 binary code. Supports decoding of forbidden instructions, provides information about cycle count, which registers the instruction accesses and which status flags are affected. Acceptable data input can be either an array of bytes, a vector of bytes or a binary file.
4//!
5//!# Quick Start
6//!
7//!```
8//!extern crate disasm6502;
9//!
10//!fn main()
11//!{
12//! let bytes = vec![0x05, 0x0B, 0x6C, 0x01, 0x02,
13//! 0x0A, 0xA2, 0xFF, 0x20, 0x02,
14//! 0xFD, 0x78, 0xD0, 0xFC, 0x1D,
15//! 0x05, 0x1E, 0x04, 0x15, 0x02,
16//! 0x96, 0xAB, 0x58, 0x61, 0x01,
17//! 0x91, 0xFB];
18//!
19//! // disassemble...
20//! let instructions = disasm6502::from_array(&bytes).unwrap();
21//!
22//! // ...and print!
23//! for i in instructions.iter() {
24//! println!("{}", i);
25//! }
26//!}
27//!```
28pub mod error;
29pub mod instruction;
30
31use error::Result;
32use instruction::Instruction;
33use std::fs::File;
34use std::io::prelude::*;
35use std::path::Path;
36
37/// Disassembles data from binary file using $0000 as start address.
38///
39/// # Examples
40///
41/// ```
42/// extern crate disasm6502;
43///
44/// // first instruction will be located at $0000
45/// let instructions = disasm6502::from_file("examples/data.bin").unwrap();
46/// ```
47pub fn from_file(filename: &str) -> Result<Vec<Instruction>> {
48 from_addr_file(filename, 0x0000)
49}
50
51/// Disassembles data from binary file using a custom start address.
52///
53/// # Examples
54///
55/// ```
56/// extern crate disasm6502;
57///
58/// // first instruction will be located at $0800
59/// let instructions = disasm6502::from_addr_file("examples/data.bin", 0x0800).unwrap();
60/// ```
61pub fn from_addr_file(filename: &str, start_address: u16) -> Result<Vec<Instruction>> {
62 let path = Path::new(&filename);
63 let mut file = File::open(&path)?;
64 let mut bytes = Vec::new();
65 file.read_to_end(&mut bytes)?;
66
67 from_addr_array(&bytes, start_address)
68}
69
70/// Disassembles data from array of bytes using $0000 as start address.
71///
72/// # Examples
73///
74/// ```
75/// extern crate disasm6502;
76///
77/// let bytes = vec![0x05, 0x0B, 0x6C, 0x01, 0x02];
78///
79/// // first instruction will be located at $0000
80/// let instructions = disasm6502::from_array(&bytes).unwrap();
81/// ```
82pub fn from_array(bytes: &[u8]) -> Result<Vec<Instruction>> {
83 from_addr_array(bytes, 0x0000)
84}
85
86/// Disassembles data from array of bytes using a custom start address.
87///
88/// # Examples
89///
90/// ```
91/// extern crate disasm6502;
92///
93/// let bytes = vec![0x05, 0x0B, 0x6C, 0x01, 0x02];
94///
95/// // first instruction will be located at $0800
96/// let instructions = disasm6502::from_addr_array(&bytes, 0x0800).unwrap();
97/// ```
98pub fn from_addr_array(bytes: &[u8], start_address: u16) -> Result<Vec<Instruction>> {
99 let mut ret = Vec::<Instruction>::new();
100 let mut index: usize = 0;
101 let mut next_addr = start_address;
102
103 while index < bytes.len() {
104 let instruction = instruction::decode(next_addr, &mut index, &bytes);
105 ret.push(instruction);
106 next_addr = start_address.wrapping_add(index as u16);
107 }
108
109 Ok(ret)
110}