Skip to content

Commit

Permalink
feat: update cli ui
Browse files Browse the repository at this point in the history
  • Loading branch information
imyelo committed May 30, 2019
1 parent f944f7b commit e27472a
Show file tree
Hide file tree
Showing 2 changed files with 101 additions and 63 deletions.
16 changes: 12 additions & 4 deletions bin/padoracle.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,9 +15,10 @@ const ui = jsx('./ui')
$ padoracle <challenge-script> --iv-cipher <iv-cipher> --size 16
Options
challenge-script A script which sends the decryption challenge to the target system.
--iv-cipher An iv-cipher pair which can pass the padding check (with base64 encoded).
--size Size of each block (in bytes).
challenge-script A script which sends the decryption challenge to the target system.
--iv-cipher An iv-cipher pair which can pass the padding check (with base64 encoded).
--size, -s Size of each block (in bytes).
--concurrency, -c Concurrency, Infinity by default.
Examples
$ padoracle ./examples/crackme-challenge.js --iv-cipher UGFkT3JhY2xlOml2L2NiYyiFmLTj7lhu4mAJHakEqcIIoYU0lIUXKx+PmTaUHLV0 --size 16
Expand All @@ -28,6 +29,11 @@ const ui = jsx('./ui')
},
size: {
type: 'string',
alias: 's',
},
concurrency: {
type: 'string',
alias: 'c',
},
},
})
Expand All @@ -53,9 +59,11 @@ const ui = jsx('./ui')
throw new Error('<size> is required.')
}

const concurrency = +cli.flags.concurrency || Infinity

const iv = token.slice(0, size)
const cipher = token.slice(size)

render(React.createElement(ui, { challenge: script.default, iv, cipher }))
render(React.createElement(ui, { challenge: script.default, iv, cipher, concurrency }))

})()
148 changes: 89 additions & 59 deletions bin/ui.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,48 +17,76 @@ function alloc(size, value) {
}

const bus = new EventEmitter()
const print = (message) => bus.emit('message', message)
const print = message => bus.emit('message', message)

const Block = ({ cracker, block }) => {
const [cipher, setCipher] = React.useState([])
const [intermediary, setIntermediary] = React.useState([])
const [vector, setVector] = React.useState([])
const [plain, setPlain] = React.useState([])
const [isTampered, setIsTampered] = React.useState(false)

React.useEffect(() => {
if (!cracker) {
return
}
const subscribe = (name, handler) => cracker.broadcast.addListener(name, (data) => {
if (block !== data.block) {
return
}
handler(data)
})
const subscribe = (name, handler) =>
cracker.broadcast.addListener(name, data => {
if (block !== data.block) {
return
}
handler(data)
})
let size, slice

subscribe(EVENTS.CRACK_BLOCK_START, ({ iv, cipher, block }) => {
const size = iv.length
const slice = (size => (buf, block) =>
size = iv.length
slice = (size => (buf, block) =>
buf.slice(block * size, (block + 1) * size))(size)

setCipher(slice(cipher, block))
setIntermediary(alloc(size, '??'))
setVector(
block === 0 ? iv : slice(cipher, block - 1)
)
setVector(block === 0 ? iv : slice(cipher, block - 1))
setPlain(alloc(size, '??'))
setIsTampered(true)
})

subscribe(
EVENTS.CRACK_BLOCK_UPDATE_INTERMEDIARY_AT,
({ position, value }) => {
setIntermediary(intermediary => [
...intermediary.slice(0, position),
value,
...intermediary.slice(position + 1),
])
}
)

subscribe(EVENTS.TRAVERSING_KEY_START, ({ padding }) => {
const plain = ((size, padding) => {
let buf = alloc(size, '??')
return buf.map((v, i) => {
if (size - i > padding - 1) {
return v
}
return padding
})
})(size, padding)
setPlain(plain)
})

subscribe(EVENTS.CHALLENGE, ({ block, padding, hex, sample }) => {
print(
`Challenge start on Block ${block}, Padding ${padding}, Value ${hex} ...`
)
setVector(slice(sample, block))
})

subscribe(EVENTS.CRACK_BLOCK_UPDATE_INTERMEDIARY_AT, ({ block, position, value }) => {
setIntermediary((intermediary) => [
...intermediary.slice(0, position),
value,
...intermediary.slice(position + 1),
])
subscribe(EVENTS.TRAVERSING_KEY_END, () => {
setVector(alloc(size, '--'))
setPlain(alloc(size, '--'))
})

subscribe(EVENTS.CHALLENGE, ({ block, padding, hex }) => {
print(`Challenge start on Block ${block}, Padding ${padding}, Value ${hex} ...`)
subscribe(EVENTS.CRACK_BLOCK_END, () => {
setIsTampered(false)
})
}, [cracker, block])

Expand All @@ -76,20 +104,32 @@ const Block = ({ cracker, block }) => {
</Box>
<Box>
<Box flexDirection="column">
<Text>Cipher ({block}) : </Text>
<Text>Intermediary ({block}) : </Text>
<Text>-</Text>
{block > 0 ? (
<Text>Cipher ({block - 1}) : </Text>
) : (
<Text>Initial Vector : </Text>
)}
{
isTampered
? <div>
<Text>-</Text>
{block > 0 ? (
<Text>Cipher ({block - 1}) (Tampered) : </Text>
) : (
<Text>Initial Vector (Tampered) : </Text>
)}
<Text>Plain (Tampered) : </Text>
</div>
: <div />
}
</Box>
<Box flexDirection="column">
<Text>{format(cipher, block)}</Text>
<Text>{format(intermediary)}</Text>
<Text>-</Text>
<Text>{format(vector)}</Text>
{
isTampered
? <div>
<Text>-</Text>
<Text>{format(vector)}</Text>
<Text>{format(plain)}</Text>
</div>
: <div />
}
</Box>
</Box>
<Divider />
Expand All @@ -99,9 +139,9 @@ const Block = ({ cracker, block }) => {

const Divider = () => (
<div>
<div></div>
<div />
<div>--------------------</div>
<div></div>
<div />
</div>
)

Expand All @@ -120,25 +160,22 @@ const Messages = () => {
let [messages, setMessages] = React.useState([])

React.useEffect(() => {
bus.on('message', (message) => {
setMessages((messages) => [
...messages,
message,
])
bus.on('message', message => {
setMessages(messages => [...messages, message])
})
}, [])

return <div>
<div>Messages:</div>
{
messages.slice(-1 * LEN).map((msg, i) => (
return (
<div>
<div>Messages:</div>
{messages.slice(-1 * LEN).map((msg, i) => (
<div key={i}>{msg}</div>
))
}
</div>
))}
</div>
)
}

function App({ challenge, iv, cipher }) {
function App({ challenge, iv, cipher, concurrency }) {
const [cracker, setCracker] = React.useState()
const [crackResult, setCrackResult] = React.useState({})

Expand All @@ -147,23 +184,16 @@ function App({ challenge, iv, cipher }) {
React.useEffect(() => {
let cracker = new Cracker()
setCracker(cracker)
cracker.crack(iv, cipher, challenge)
.then((result) => setCrackResult(result))
cracker.crack(iv, cipher, challenge, concurrency).then(result => setCrackResult(result))
}, [])

return (
<Box flexDirection="column">
{
blocks.map((v, i) => (
<Block cracker={cracker} block={i} key={i} />
))
}
{blocks.map((v, i) => (
<Block cracker={cracker} block={i} key={i} />
))}
<Divider />
{
crackResult.plain
? <Result plain={crackResult.plain} />
: <Messages />
}
{crackResult.plain ? <Result plain={crackResult.plain} /> : <Messages />}
<Divider />
</Box>
)
Expand Down

0 comments on commit e27472a

Please sign in to comment.