#include <string.h>
#include <stdio.h>
#define DUMMY "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA" \
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
\
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
\
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
\
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
\
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
int
angel
(
)
;
int
devil
(
)
;
char
*
dummya
=
DUMMY
"A"
;
char
*
dummyb
=
DUMMY
"B"
;
int
main
(
)
{
if
(
strcmp
(
dummya
,
dummyb
)
!=
0
)
{
return
angel
(
)
;
}
else
{
return
devil
(
)
;
}
}
int
angel
(
)
{
fprintf
(
stdout
,
". ,\n"
)
;
fprintf
(
stdout
,
")). -===- ,((\n"
)
;
fprintf
(
stdout
,
"))). ,(((\n"
)
;
fprintf
(
stdout
,
"))))). .:::. ,((((((\n"
)
;
fprintf
(
stdout
,
"))))))))). :. .: ,(((((((('\n"
)
;
fprintf
(
stdout
,
"`))))))))))). : - : ,((((((((((((\n"
)
;
fprintf
(
stdout
,
"))))))))))))))))_:' ':_((((((((((((((('\n"
)
;
fprintf
(
stdout
,
" `)))))))))))).-' \\___/ '-._(((((((((((\n"
)
;
fprintf
(
stdout
,
" `))))_._.-' __)( )(_ '-._._(((('\n"
)
;
fprintf
(
stdout
,
" `))'---)___)))'\\_ _/'((((__(---'(('\n"
)
;
fprintf
(
stdout
,
" `))))))))))))|' '|(((((((((((('\n"
)
;
fprintf
(
stdout
,
" `)))))))))/' '\
\
(
(
(
(
(
(
(
(
(
'
\
n
"
)
;
fprintf(stdout, "
`
)
)
)
)
)
)
)
|
|
(
(
(
(
(
(
(
'\n");
fprintf(stdout, " `))))))| |(((((('
\
n
");
fprintf(stdout, "
/
' '
\
\
\
n
");
fprintf(stdout, "
/
' '
\
\
\
n
");
fprintf(stdout, "
/
' '
\
\
\
n
");
fprintf(stdout, "
/
' '
\
\
\
n
");
fprintf(stdout, "
'---..___..---'
\
\
\
n
");
return 0;
}
int devil() {
fprintf(stdout, "
_
.
--
-
*
*
""
*
*
-
.
\
n
");
fprintf(stdout, "
.
_
.
-
' /|`.\n");
fprintf(stdout, " \`.'
/
|
`
.
\
n
");
fprintf(stdout, "
V
(
;
\
\
\
n
");
fprintf(stdout, "
L
_
.
-
-
.
`
' \\\n");
fprintf(stdout, " / `-. _.'
\
\
;
\
n
");
fprintf(stdout, "
:
_
_
;
_
|
\
n
");
fprintf(stdout, "
:
`
-
.
___
.
+
-
*
\
"
': ` ; .'
`
.
|
\
n
");
fprintf(stdout, "
|
`
-
/
`
--
*
' / / /`.\\|\n");
fprintf(stdout, ": : \\ :`.| ;\n");
fprintf(stdout, "| | . ;/ .'
' /\n");
fprintf(stdout, ": : / ` :__.'
\
n
");
fprintf(stdout, "
\
`
.
_
.
-
' / |\n");
fprintf(stdout, " : ) : ;\n");
fprintf(stdout, " :----.._ | /\n");
fprintf(stdout, " : .-. `. /\n");
fprintf(stdout, " \\ `._ /\n");
fprintf(stdout, " /`- /\n");
fprintf(stdout, " : .'
\
n
");
fprintf(stdout, "
\
\
)
.
-
'\n");
fprintf(stdout, " `-----*\"'
\
n
"
)
;
return
0
;
}
$dummyText = str_pad('', 64, 'A');
function replaceDummyText($input, $replacment, $position)
return substr_replace($input, $replacment, $position, strlen($replacment));
function findDummyText($filestring, $dummyText)
$pos = 0;
$chunks = str_split($filestring, 64);
foreach ($chunks as $chunk) {
if ($chunk == $dummyText) {
break 1;
$pos++;
return $pos*64;
// read in the original binary file in
$filestring = file_get_contents($inFile);
// find the place where we have the dummy string and its at start of a 64 byte block
$pos = findDummyText($filestring, $dummyText);
printf('I want to replace %d bytes at position %d in %s'.PHP_EOL, 128, $pos, $inFile);
$firstPart = substr($filestring, 0, $pos);
//find the IV up to the point we want to insert then print that out
$iv = md5_hash($firstPart);
printf('Chaining variable up to that point is %s'.PHP_EOL, $iv);
if (!file_exists(__DIR__.'/a')) {
print('Run fastcoll to generate a 2 block collision in MD5'.PHP_EOL);
return;
// replace the dummy text at the correct location
$good = replaceDummyText($filestring, file_get_contents(__DIR__.'/a'), $pos);
$bad = replaceDummyText($filestring, file_get_contents(__DIR__.'/b'), $pos);
// find the secod dummy string
$secondDummyTextStart = strpos($good, str_pad('', 191, 'A'));
// serach back from where we inserted the collision first time so we can grab the whole
// 192 bytes and use it to replace the second string
while ('A' == substr($filestring, $pos-1, 1)) {
--$pos;
//the 192 butes of str1
$replacement = substr($good, $pos, 192);
// replace str1 with 192 bytes cut from of the files
// the file it came from will then compare str1 and str2 to 0
$good = replaceDummyText($good, $replacement, $secondDummyTextStart);
file_put_contents(__DIR__.'/devil', $good);
printf('Just output new file %s with hash %s'.PHP_EOL, __DIR__.'/devil', md5($good));
$bad = replaceDummyText($bad, $replacement, $secondDummyTextStart);
file_put_contents(__DIR__.'/angel', $bad);
printf('Just output new file %s with hash %s'.PHP_EOL, __DIR__.'/angel', md5($bad));
&
lt
;
?
php
include
__DIR__
.
'/MD5.php'
;
$
inFile
=
__DIR__
.
'/demo'
;
$
dummyText
=
str_pad
(
''
,
64
,
'A'
)
;
function
replaceDummyText
(
$
input
,
$
replacment
,
$
position
)
{
return
substr_replace
(
$
input
,
$
replacment
,
$
position
,
strlen
(
$
replacment
)
)
;
}
function
findDummyText
(
$
filestring
,
$
dummyText
)
{
$
pos
=
0
;
$
chunks
=
str_split
(
$
filestring
,
64
)
;
foreach
(
$
chunks
as
$
chunk
)
{
if
(
$
chunk
==
$
dummyText
)
{
break
1
;
}
$
pos
++
;
}
return
$
pos
*
64
;
}
/
/
read
in
the
original
binary
file
in
$
filestring
=
file_get_contents
(
$
inFile
)
;
/
/
find
the
place
where
we
have
the
dummy
string
and
its
at
start
of
a
64
byte
block
$
pos
=
findDummyText
(
$
filestring
,
$
dummyText
)
;
printf
(
'I want to replace %d bytes at position %d in %s'
.
PHP_EOL
,
128
,
$
pos
,
$
inFile
)
;
$
firstPart
=
substr
(
$
filestring
,
0
,
$
pos
)
;
/
/
find
the
IV
up
to
the
point
we
want
to
insert
then
print
that
out
$
iv
=
md5_hash
(
$
firstPart
)
;
printf
(
'Chaining variable up to that point is %s'
.
PHP_EOL
,
$
iv
)
;
if
(
!
file_exists
(
__DIR__
.
'/a'
)
)
{
print
(
'Run fastcoll to generate a 2 block collision in MD5'
.
PHP_EOL
)
;
return
;
}
/
/
replace
the
dummy
text
at
the
correct
location
$
good
=
replaceDummyText
(
$
filestring
,
file_get_contents
(
__DIR__
.
'/a'
)
,
$
pos
)
;
$
bad
=
replaceDummyText
(
$
filestring
,
file_get_contents
(
__DIR__
.
'/b'
)
,
$
pos
)
;
/
/
find
the
secod
dummy
string
$
secondDummyTextStart
=
strpos
(
$
good
,
str_pad
(
''
,
191
,
'A'
)
)
;
/
/
serach
back
from
where
we
inserted
the
collision
first
time
so
we
can
grab
the
whole
/
/
192
bytes
and
use
it
to
replace
the
second
string
while
(
'A'
==
substr
(
$
filestring
,
$
pos
-
1
,
1
)
)
{
--
$
pos
;
}
/
/
the
192
butes
of
str1
$
replacement
=
substr
(
$
good
,
$
pos
,
192
)
;
/
/
replace
str1
with
192
bytes
cut
from
of
the
files
/
/
the
file
it
came
from
will
then
compare
str1
and
str2
to
0
$
good
=
replaceDummyText
(
$
good
,
$
replacement
,
$
secondDummyTextStart
)
;
file_put_contents
(
__DIR__
.
'/devil'
,
$
good
)
;
printf
(
'Just output new file %s with hash %s'
.
PHP_EOL
,
__DIR__
.
'/devil'
,
md5
(
$
good
)
)
;
$
bad
=
replaceDummyText
(
$
bad
,
$
replacement
,
$
secondDummyTextStart
)
;
file_put_contents
(
__DIR__
.
'/angel'
,
$
bad
)
;
printf
(
'Just output new file %s with hash %s'
.
PHP_EOL
,
__DIR__
.
'/angel'
,
md5
(
$
bad
)
)
;
$ php long_egg.php
I want to replace 128 bytes at position 3008 in /var/www/html/md5collisions/longEgg/demo
Chainring variable up to that point is <strong>a2330164cee76a94d8779f4a2bdfa6a2</strong>
Run fastcoll to generate a 2 block collision in MD5