Merge pull request #1 from jakcron/master

ctrtool: Updated exheader validation and ncch spec/flag recognition
This commit is contained in:
profi200
2015-09-15 19:04:13 +02:00
53 changed files with 1352 additions and 22806 deletions
+3 -3
View File
@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="utf-8"?>
<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Project DefaultTargets="Build" ToolsVersion="14.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<ItemGroup Label="ProjectConfigurations">
<ProjectConfiguration Include="Debug|Win32">
<Configuration>Debug</Configuration>
@@ -18,13 +18,13 @@
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<PlatformToolset>v110</PlatformToolset>
<PlatformToolset>v140</PlatformToolset>
<CharacterSet>Unicode</CharacterSet>
<WholeProgramOptimization>true</WholeProgramOptimization>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<PlatformToolset>v110</PlatformToolset>
<PlatformToolset>v140</PlatformToolset>
<CharacterSet>Unicode</CharacterSet>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+114 -97
View File
@@ -126,6 +126,58 @@ int exheader_programid_valid(exheader_context* ctx)
return 1;
}
void exheader_deserialise_arm11localcaps_permissions(exheader_arm11systemlocalcaps_deserialised *caps, const exheader_arm11systemlocalcaps *arm11)
{
int i;
memset(caps, 0, sizeof(exheader_arm11systemlocalcaps_deserialised));
memcpy(caps->program_id, arm11->programid, 8);
caps->core_version = getle32(arm11->coreversion);
caps->enable_l2_cache = (arm11->flag[0] >> 0) & 1;
caps->use_additional_cores = (arm11->flag[0] >> 1) & 1;
caps->new3ds_systemmode = (arm11->flag[1] >> 0) & 15;
caps->ideal_processor = (arm11->flag[2] >> 0) & 3;
caps->affinity_mask = (arm11->flag[2] >> 2) & 3;
caps->old3ds_systemmode = (arm11->flag[2] >> 4) & 15;
caps->priority = (s8)arm11->flag[3];
// storage info
if (arm11->storageinfo.otherattributes & 2) {
caps->extdata_id = 0;
for (i = 0; i < 3; i++)
caps->other_user_saveid[i] = 0;
caps->use_other_variation_savedata = 0;
for (i = 0; i < 3; i++)
caps->accessible_saveid[i] = 0xfffff & (getle64(arm11->storageinfo.accessibleuniqueids) >> 20 * (2 - i));
for (i = 0; i < 3; i++)
caps->accessible_saveid[i+3] = 0xfffff & (getle64(arm11->storageinfo.extsavedataid) >> 20 * (2 - i));
}
else {
caps->extdata_id = getle64(arm11->storageinfo.extsavedataid);
for (i = 0; i < 3; i++)
caps->other_user_saveid[i] = 0xfffff & (getle64(arm11->storageinfo.accessibleuniqueids) >> 20 * (2 - i));
caps->use_other_variation_savedata = (getle64(arm11->storageinfo.accessibleuniqueids) >> 60) & 1;
for (i = 0; i < 6; i++)
caps->accessible_saveid[i] = 0;
}
caps->system_saveid[0] = getle32(arm11->storageinfo.systemsavedataid);
caps->system_saveid[1] = getle32(arm11->storageinfo.systemsavedataid + 4);
caps->accessinfo = getle64(arm11->storageinfo.accessinfo) & ~((u64)0xff00000000000000);
// Service Access Control
for (i = 0; i < 34; i++)
strncpy(caps->service_access_control[i], (char*)arm11->serviceaccesscontrol[i], 8);
caps->resource_limit_category = arm11->resourcelimitcategory;
}
int exheader_process(exheader_context* ctx, u32 actions)
{
exheader_determine_key(ctx, actions);
@@ -135,13 +187,13 @@ int exheader_process(exheader_context* ctx, u32 actions)
if (ctx->header.codesetinfo.flags.flag & 1)
ctx->compressedflag = 1;
exheader_deserialise_arm11localcaps_permissions(&ctx->system_local_caps, &ctx->header.arm11systemlocalcaps);
if (actions & VerifyFlag)
exheader_verify(ctx);
if (actions & InfoFlag)
{
exheader_print(ctx);
}
exheader_print(ctx);
return 1;
}
@@ -397,11 +449,10 @@ void exheader_print_arm11accessinfo(exheader_context* ctx)
{
char str[100];
u64 i, bit;
u64 accessinfo = 0xffffffffffffff & getle64(ctx->header.arm11systemlocalcaps.storageinfo.accessinfo);
for(i = 0; i < 56; i++)
{
bit = ((u64)1 << i);
if((accessinfo & bit) == bit)
if((ctx->system_local_caps.accessinfo & bit) == bit)
fprintf(stdout, " > %s\n",exheader_print_accessinfobit((u32)i,str));
}
}
@@ -410,72 +461,21 @@ void exheader_print_arm11storageinfo(exheader_context* ctx)
{
u32 i;
// Storage Info
u32 systemsaveID[2];
u64 extdataID;
u32 otherusersaveID[3];
u32 accessiblesaveID[6];
u8 otherattibutes = ctx->header.arm11systemlocalcaps.storageinfo.otherattributes;
u8 accessOtherVariationSavedata = (getle64(ctx->header.arm11systemlocalcaps.storageinfo.accessibleuniqueids) & 0x1000000000000000) == 0x1000000000000000;
systemsaveID[0] = getle32(ctx->header.arm11systemlocalcaps.storageinfo.systemsavedataid);
systemsaveID[1] = getle32(ctx->header.arm11systemlocalcaps.storageinfo.systemsavedataid+4);
extdataID = getle64(ctx->header.arm11systemlocalcaps.storageinfo.extsavedataid);
for(i = 0; i < 3; i++)
{
accessiblesaveID[i] = 0xfffff & (getle64(ctx->header.arm11systemlocalcaps.storageinfo.accessibleuniqueids) >> 20*(2-i));
otherusersaveID[i] = 0xfffff & (getle64(ctx->header.arm11systemlocalcaps.storageinfo.accessibleuniqueids) >> 20*(2-i));
}
for(i = 0; i < 3; i++)
{
accessiblesaveID[i+3] = 0xfffff & (getle64(ctx->header.arm11systemlocalcaps.storageinfo.extsavedataid) >> 20*(2-i));
}
if(otherattibutes & 2)
{
extdataID = 0;
for(i = 0; i < 3; i++)
otherusersaveID[i] = 0;
}
else
{
for(i = 0; i < 6; i++)
accessiblesaveID[i] = 0;
}
fprintf(stdout, "Ext savedata id: 0x%08"PRIx64"\n",extdataID);
fprintf(stdout, "Ext savedata id: 0x%"PRIx64"\n",ctx->system_local_caps.extdata_id);
for(i = 0; i < 2; i++)
fprintf(stdout, "System savedata id %d: 0x%08x %s\n",i+1,systemsaveID[i],exheader_getvalidstring(ctx->validsystemsaveID[i]));
fprintf(stdout, "System savedata id %d: 0x%x %s\n",i+1, ctx->system_local_caps.system_saveid[i],exheader_getvalidstring(ctx->validsystemsaveID[i]));
for(i = 0; i < 3; i++)
fprintf(stdout, "OtherUserSaveDataId%d: 0x%05x\n",i+1,otherusersaveID[i]);
fprintf(stdout, "OtherUserSaveDataId%d: 0x%x\n",i+1, ctx->system_local_caps.other_user_saveid[i]);
fprintf(stdout, "Accessible Savedata Ids:\n");
for(i = 0; i < 6; i++)
{
if(accessiblesaveID[i] != 0x00000)
fprintf(stdout, " > 0x%05x\n",accessiblesaveID[i]);
if(ctx->system_local_caps.accessible_saveid[i] != 0x00000)
fprintf(stdout, " > 0x%05x\n", ctx->system_local_caps.accessible_saveid[i]);
}
fprintf(stdout, "Other Variation Saves: %s\n", accessOtherVariationSavedata ? "Accessible" : "Inaccessible");
if(ctx->validaccessinfo == Unchecked)
memdump(stdout, "Access info: ", ctx->header.arm11systemlocalcaps.storageinfo.accessinfo, 7);
else if(ctx->validaccessinfo == Good)
memdump(stdout, "Access info (GOOD): ", ctx->header.arm11systemlocalcaps.storageinfo.accessinfo, 7);
else
memdump(stdout, "Access info (FAIL): ", ctx->header.arm11systemlocalcaps.storageinfo.accessinfo, 7);
exheader_print_arm11accessinfo(ctx);
fprintf(stdout, "Other attributes: %02X", ctx->header.arm11systemlocalcaps.storageinfo.otherattributes);
/*
if(otherattibutes & 1)
fprintf(stdout," [no use romfs]");
if(otherattibutes & 2)
fprintf(stdout," [use extended savedata access control]");
*/
printf("\n");
fprintf(stdout, "Other Variation Saves: %s\n", ctx->system_local_caps.use_other_variation_savedata ? "Accessible" : "Inaccessible");
fprintf(stdout, "Access info: 0x%"PRIx64" %s\n", ctx->system_local_caps.accessinfo,exheader_getvalidstring(ctx->validaccessinfo));
exheader_print_arm11accessinfo(ctx);
}
int exheader_signature_verify(exheader_context* ctx, rsakey2048* key)
@@ -486,61 +486,78 @@ int exheader_signature_verify(exheader_context* ctx, rsakey2048* key)
return ctr_rsa_verify_hash(ctx->header.accessdesc.signature, hash, key);
}
void exheader_verify(exheader_context* ctx)
{
unsigned int i;
u8 exheaderflag6[3];
u8 descflag6[3];
unsigned int i, j;
exheader_arm11systemlocalcaps_deserialised accessdesc;
exheader_deserialise_arm11localcaps_permissions(&accessdesc, &ctx->header.accessdesc.arm11systemlocalcaps);
ctx->validsystemsaveID[0] = Good;
ctx->validsystemsaveID[1] = Good;
ctx->validaccessinfo = Good;
ctx->validcoreversion = Good;
ctx->validprogramid = Good;
ctx->validpriority = Good;
ctx->validaffinitymask = Good;
ctx->valididealprocessor = Good;
ctx->validold3dssystemmode = Good;
ctx->validnew3dssystemmode = Good;
ctx->validenablel2cache = Good;
ctx->validuseadditionalcores = Good;
ctx->validservicecontrol = Good;
for(i=0; i<8; i++)
{
if (0 == (ctx->header.arm11systemlocalcaps.programid[i] & ~ctx->header.accessdesc.arm11systemlocalcaps.programid[i]))
if (ctx->system_local_caps.program_id[i] == accessdesc.program_id[i] || accessdesc.program_id[i] == 0xFF)
continue;
ctx->validprogramid = Fail;
break;
}
// Ideal Proccessor
exheaderflag6[0] = (ctx->header.arm11systemlocalcaps.flag>>0)&0x3;
descflag6[0] = (ctx->header.accessdesc.arm11systemlocalcaps.flag>>0)&0x3;
// Affinity Mask
exheaderflag6[1] = (ctx->header.arm11systemlocalcaps.flag>>2)&0x3;
descflag6[1] = (ctx->header.accessdesc.arm11systemlocalcaps.flag>>2)&0x3;
// System Mode
//exheaderflag6[2] = (ctx->header.arm11systemlocalcaps.flag>>4)&0xf;
//descflag6[2] = (ctx->header.accessdesc.arm11systemlocalcaps.flag>>4)&0xf;
if (ctx->system_local_caps.core_version != accessdesc.core_version)
ctx->validcoreversion = Fail;
if (ctx->header.accessdesc.arm11systemlocalcaps.priority > ctx->header.arm11systemlocalcaps.priority || ctx->header.arm11systemlocalcaps.priority > 127)
if (ctx->system_local_caps.priority < accessdesc.priority)
ctx->validpriority = Fail;
if((1<<exheaderflag6[0] & descflag6[0]) == 0)
if((1<<ctx->system_local_caps.ideal_processor & accessdesc.ideal_processor) == 0)
ctx->valididealprocessor = Fail;
if (exheaderflag6[1] & ~descflag6[1])
if (ctx->system_local_caps.affinity_mask & ~accessdesc.affinity_mask)
ctx->validaffinitymask = Fail;
if (ctx->system_local_caps.old3ds_systemmode > accessdesc.old3ds_systemmode)
ctx->validold3dssystemmode = Fail;
if (ctx->system_local_caps.new3ds_systemmode > accessdesc.new3ds_systemmode)
ctx->validnew3dssystemmode = Fail;
// Storage Info Verify
if(0 != (getle32(ctx->header.arm11systemlocalcaps.storageinfo.systemsavedataid) & ~getle32(ctx->header.accessdesc.arm11systemlocalcaps.storageinfo.systemsavedataid)))
if(ctx->system_local_caps.system_saveid[0] & ~accessdesc.system_saveid[0])
ctx->validsystemsaveID[0] = Fail;
if(0 != (getle32(ctx->header.arm11systemlocalcaps.storageinfo.systemsavedataid+4) & ~getle32(ctx->header.accessdesc.arm11systemlocalcaps.storageinfo.systemsavedataid+4)))
if(ctx->system_local_caps.system_saveid[1] & ~accessdesc.system_saveid[1])
ctx->validsystemsaveID[1] = Fail;
for(i=0; i<7; i++)
{
if(0 == (ctx->header.arm11systemlocalcaps.storageinfo.accessinfo[i] & ~ctx->header.accessdesc.arm11systemlocalcaps.storageinfo.accessinfo[i]))
continue;
if (ctx->system_local_caps.accessinfo & ~accessdesc.accessinfo)
ctx->validaccessinfo = Fail;
break;
// Service Access Control
for (i = 0; i < 34; i++) {
if (strlen(ctx->system_local_caps.service_access_control[i]) == 0)
continue;
for (j = 0; j < 34; j++) {
if (strcmp(ctx->system_local_caps.service_access_control[i], accessdesc.service_access_control[j]) == 0)
break;
}
if (strcmp(ctx->system_local_caps.service_access_control[i], accessdesc.service_access_control[j]) == 0)
continue;
ctx->validservicecontrol = Fail;
}
if (ctx->usersettings)
@@ -609,21 +626,21 @@ void exheader_print(exheader_context* ctx)
fprintf(stdout, "Program id: %016"PRIx64" %s\n", getle64(ctx->header.arm11systemlocalcaps.programid), exheader_getvalidstring(ctx->validprogramid));
fprintf(stdout, "Core version: 0x%X\n", getle32(ctx->header.arm11systemlocalcaps.coreversion));
fprintf(stdout, "System mode: 0x%X\n", (ctx->header.arm11systemlocalcaps.flag>>4)&0xF);
fprintf(stdout, "Ideal processor: %d %s\n", (ctx->header.arm11systemlocalcaps.flag>>0)&0x3, exheader_getvalidstring(ctx->valididealprocessor));
fprintf(stdout, "Affinity mask: %d %s\n", (ctx->header.arm11systemlocalcaps.flag>>2)&0x3, exheader_getvalidstring(ctx->validaffinitymask));
fprintf(stdout, "Main thread priority: %d %s\n", ctx->header.arm11systemlocalcaps.priority, exheader_getvalidstring(ctx->validpriority));
fprintf(stdout, "System mode: %d %s\n", ctx->system_local_caps.old3ds_systemmode, exheader_getvalidstring(ctx->validold3dssystemmode));
fprintf(stdout, "System mode (New3DS): %d %s\n", ctx->system_local_caps.new3ds_systemmode, exheader_getvalidstring(ctx->validnew3dssystemmode));
fprintf(stdout, "Ideal processor: %d %s\n", ctx->system_local_caps.ideal_processor, exheader_getvalidstring(ctx->valididealprocessor));
fprintf(stdout, "Affinity mask: %d %s\n", ctx->system_local_caps.affinity_mask, exheader_getvalidstring(ctx->validaffinitymask));
fprintf(stdout, "Main thread priority: %d %s\n", ctx->system_local_caps.priority, exheader_getvalidstring(ctx->validpriority));
// print resource limit descriptor too? currently mostly zeroes...
exheader_print_arm11storageinfo(ctx);
exheader_print_arm11kernelcapabilities(ctx);
exheader_print_arm9accesscontrol(ctx);
for(i=0; i<0x20; i++)
fprintf(stdout, "Service access: %s\n", exheader_getvalidstring(ctx->validservicecontrol));
for(i=0; i<34; i++)
{
if (getle64(ctx->header.arm11systemlocalcaps.serviceaccesscontrol[i]) != 0x0000000000000000UL)
fprintf(stdout, "Service access: %.8s\n", ctx->header.arm11systemlocalcaps.serviceaccesscontrol[i]);
if (strlen(ctx->system_local_caps.service_access_control[i]) > 0)
fprintf(stdout, " > %s\n", ctx->system_local_caps.service_access_control[i]);
}
fprintf(stdout, "Reslimit category: %02X\n", ctx->header.arm11systemlocalcaps.resourcelimitcategory);
}
+39 -5
View File
@@ -57,16 +57,41 @@ typedef struct
{
u8 programid[8];
u8 coreversion[4];
u8 reserved0[2];
u8 flag;
u8 priority;
u8 flag[4];
u8 resourcelimitdescriptor[0x10][2];
exheader_storageinfo storageinfo;
u8 serviceaccesscontrol[0x20][8];
u8 reserved[0x1f];
u8 serviceaccesscontrol[34][8];
u8 reserved[0xf];
u8 resourcelimitcategory;
} exheader_arm11systemlocalcaps;
typedef struct
{
u8 program_id[8];
u32 core_version;
// flag
u8 enable_l2_cache;
u8 use_additional_cores;
u8 new3ds_systemmode;
u8 ideal_processor;
u8 affinity_mask;
u8 old3ds_systemmode;
s8 priority;
// storageinfo
u64 extdata_id;
u32 other_user_saveid[3];
u8 use_other_variation_savedata;
u32 accessible_saveid[3];
u32 system_saveid[2];
u64 accessinfo;
char service_access_control[34][10];
u8 resource_limit_category;
} exheader_arm11systemlocalcaps_deserialised;
typedef struct
{
u8 descriptors[28][4];
@@ -115,6 +140,9 @@ typedef struct
u32 offset;
u32 size;
exheader_header header;
exheader_arm11systemlocalcaps_deserialised system_local_caps;
ctr_aes_context aes;
ctr_rsa_context rsa;
int compressedflag;
@@ -123,8 +151,14 @@ typedef struct
int validpriority;
int validaffinitymask;
int valididealprocessor;
int validold3dssystemmode;
int validnew3dssystemmode;
int validenablel2cache;
int validuseadditionalcores;
int validcoreversion;
int validsystemsaveID[2];
int validaccessinfo;
int validservicecontrol;
int validsignature;
} exheader_context;
+14 -7
View File
@@ -540,6 +540,17 @@ static const char* contenttypetostring(unsigned char flags)
case 2: return "Manual";
case 3: return "Child";
case 4: return "Trial";
case 5: return "Extended System Update";
default: return "Unknown";
}
}
static const char* contentplatformtostring(unsigned char platform)
{
switch (platform)
{
case 1: return "CTR";
case 2: return "SNAKE";
default: return "Unknown";
}
}
@@ -566,6 +577,7 @@ void ncch_print(ncch_context* ctx)
fprintf(stdout, "Partition id: %016"PRIx64"\n", getle64(header->partitionid));
fprintf(stdout, "Maker code: %04x\n", getle16(header->makercode));
fprintf(stdout, "Version: %04x\n", getle16(header->version));
fprintf(stdout, "Title seed check: %08x\n", getle32(header->seedcheck));
fprintf(stdout, "Program id: %016"PRIx64"\n", getle64(header->programid));
if(ctx->logohashcheck == Unchecked)
memdump(stdout, "Logo hash: ", header->logohash, 0x20);
@@ -587,16 +599,11 @@ void ncch_print(ncch_context* ctx)
fprintf(stdout, " > Crypto key: None\n");
else if (header->flags[7] & 1)
fprintf(stdout, " > Crypto key: %s\n", programid_is_system(header->programid)? "Fixed":"Zeros");
else if (header->flags[3] & 1)
fprintf(stdout, " > Crypto key: Secure2\n");
else if (header->flags[3] & 10)
fprintf(stdout, " > Crypto key: secure3 (New 3DS)\n");
else
fprintf(stdout, " > Crypto key: Secure\n");
fprintf(stdout, " > Crypto key: Secure (%d)%s\n", header->flags[3], header->flags[7] & 32? " (KeyY seeded)" : "");
fprintf(stdout, " > Form type: %s\n", formtypetostring(header->flags[5]));
fprintf(stdout, " > Content type: %s\n", contenttypetostring(header->flags[5]));
if (header->flags[4] & 1)
fprintf(stdout, " > Content platform: CTR\n");
fprintf(stdout, " > Content platform: %s\n", contentplatformtostring(header->flags[4]));
if (header->flags[7] & 2)
fprintf(stdout, " > No RomFS mount\n");
+1 -1
View File
@@ -26,7 +26,7 @@ typedef struct
u8 partitionid[8];
u8 makercode[2];
u8 version[2];
u8 reserved0[4];
u8 seedcheck[4];
u8 programid[8];
u8 reserved1[0x10];
u8 logohash[0x20];
+8 -18
View File
@@ -1,19 +1,9 @@
# Makerom Sources
UTILS_OBJS = utils.o ctr_utils.o dir.o utf.o keyset.o titleid.o
CIA_OBJS = cia.o certs.o tik.o tmd.o
NCCH_OBJS = ncch.o exheader.o accessdesc.o exefs.o elf.o romfs.o romfs_import.o romfs_gen.o
NCSD_OBJS = ncsd.o cardinfo.o
SETTINGS_OBJS = user_settings.o rsf_settings.o
LIB_API_OBJS = crypto.o yaml_parser.o blz.o
OBJS = makerom.o $(UTILS_OBJS) $(LIB_API_OBJS) $(SETTINGS_OBJS) $(NCSD_OBJS) $(NCCH_OBJS) $(CIA_OBJS)
# Libraries
POLAR_OBJS = polarssl/aes.o polarssl/rsa.o polarssl/sha1.o polarssl/sha2.o polarssl/base64.o polarssl/bignum.o polarssl/padlock.o polarssl/md.o polarssl/md_wrap.o polarssl/md5.o polarssl/sha4.o
YAML_OBJS = libyaml/api.o libyaml/dumper.o libyaml/emitter.o libyaml/loader.o libyaml/parser.o libyaml/reader.o libyaml/scanner.o libyaml/writer.o
# Sources
SRC_DIR = . polarssl libyaml
OBJS = $(foreach dir,$(SRC_DIR),$(subst .c,.o,$(wildcard $(dir)/*.c)))
# Compiler Settings
LIBS = -static-libgcc -static-libstdc++
LIBS = -static-libgcc
CXXFLAGS = -I.
CFLAGS = --std=c99 -Wall -Wno-unused-but-set-variable -Wno-unused-value -I. -DMAKEROM_VER_MAJOR=$(VER_MAJOR) -DMAKEROM_VER_MINOR=$(VER_MINOR) $(MAKEROM_BUILD_FLAGS) -m64
CC = gcc
@@ -21,15 +11,15 @@ CC = gcc
# MAKEROM Build Settings
MAKEROM_BUILD_FLAGS = #-DDEBUG
VER_MAJOR = 0
VER_MINOR = 13
VER_MINOR = 14
OUTPUT = makerom
main: build
rebuild: clean build
build: $(OBJS) $(POLAR_OBJS) $(YAML_OBJS)
g++ -o $(OUTPUT) $(LIBS) $(OBJS) $(POLAR_OBJS) $(YAML_OBJS) -m64
build: $(OBJS)
g++ -o $(OUTPUT) $(LIBS) $(OBJS) -m64
clean:
rm -rf $(OUTPUT) $(OBJS) $(POLAR_OBJS) $(YAML_OBJS) *.cci *.cia *.cxi *.cfa
rm -rf $(OUTPUT) $(OBJS) *.cci *.cia *.cxi *.cfa
+2 -2
View File
@@ -44,12 +44,12 @@ int accessdesc_SignWithKey(exheader_settings *exhdrset)
memcpy(&exhdrset->acexDesc->arm9AccessControlInfo,&exhdrset->exHdr->arm9AccessControlInfo,sizeof(exhdr_ARM9AccessControlInfo));
/* Adjust Data */
u8 *flag = &exhdrset->acexDesc->arm11SystemLocalCapabilities.flag;
u8 *flag = &exhdrset->acexDesc->arm11SystemLocalCapabilities.flag[2];
u8 SystemMode = (*flag>>4)&0xF;
u8 AffinityMask = (*flag>>2)&0x3;
u8 IdealProcessor = 1<<((*flag>>0)&0x3);
*flag = (u8)(SystemMode << 4 | AffinityMask << 2 | IdealProcessor);
exhdrset->acexDesc->arm11SystemLocalCapabilities.priority /= 2;
exhdrset->acexDesc->arm11SystemLocalCapabilities.flag[3] /= 2;
/* Sign AccessDesc */
return SignAccessDesc(exhdrset->acexDesc,exhdrset->keys);
+44 -8
View File
@@ -317,7 +317,34 @@ int SetARM11SystemLocalInfoFlags(exhdr_ARM11SystemLocalCapabilities *arm11, rsf_
return EXHDR_BAD_RSF_OPT;
}
/* Flag */
/* Flag[0] */
arm11->flag[0] |= rsf->AccessControlInfo.EnableL2Cache;
if (rsf->AccessControlInfo.CpuSpeed) {
if(strcasecmp(rsf->AccessControlInfo.CpuSpeed, "256mhz") == 0)
arm11->flag[0] |= cpuspeed_268MHz << 1;
else if(strcasecmp(rsf->AccessControlInfo.CpuSpeed, "804mhz") == 0)
arm11->flag[0] |= cpuspeed_804MHz << 1;
else {
fprintf(stderr, "[EXHEADER ERROR] Invalid cpu speed: 0x%s\n", rsf->AccessControlInfo.CpuSpeed);
return EXHDR_BAD_RSF_OPT;
}
}
else
arm11->flag[0] |= cpuspeed_268MHz << 1;
/* Flag[1] (SystemModeExt) */
u8 systemModeExt = 0;
if (rsf->AccessControlInfo.SystemModeExt) {
systemModeExt = strtol(rsf->AccessControlInfo.SystemModeExt, NULL, 0);
if (systemModeExt > 15) {
fprintf(stderr, "[EXHEADER ERROR] Unexpected SystemModeExt: 0x%x. Expected range: 0x0 - 0xf\n", systemModeExt);
return EXHDR_BAD_RSF_OPT;
}
arm11->flag[1] = systemModeExt & 0xf;
}
/* Flag[2] */
u8 affinityMask = 0;
u8 idealProcessor = 0;
u8 systemMode = 0;
@@ -343,9 +370,9 @@ int SetARM11SystemLocalInfoFlags(exhdr_ARM11SystemLocalCapabilities *arm11, rsf_
return EXHDR_BAD_RSF_OPT;
}
}
arm11->flag = (u8)(systemMode << 4 | affinityMask << 2 | idealProcessor);
arm11->flag[2] = (u8)(systemMode << 4 | affinityMask << 2 | idealProcessor);
/* Thread Priority */
/* flag[3] (Thread Priority) */
if(rsf->AccessControlInfo.Priority){
u8 priority = strtoul(rsf->AccessControlInfo.Priority,NULL,0);
if(GetAppType(rsf) == processtype_APPLICATION)
@@ -354,7 +381,7 @@ int SetARM11SystemLocalInfoFlags(exhdr_ARM11SystemLocalCapabilities *arm11, rsf_
fprintf(stderr,"[EXHEADER ERROR] Invalid Priority: %d\n",priority);
return EXHDR_BAD_RSF_OPT;
}
arm11->priority = priority;
arm11->flag[3] = priority;
}
else{
ErrorParamNotFound("AccessControlInfo/Priority");
@@ -479,8 +506,13 @@ void SetARM11StorageInfoSystemSaveDataId(exhdr_ARM11SystemLocalCapabilities *arm
void SetARM11StorageInfoExtSaveDataId(exhdr_ARM11SystemLocalCapabilities *arm11, rsf_settings *rsf)
{
if(rsf->AccessControlInfo.ExtSaveDataId)
u64_to_u8(arm11->storageInfo.extSavedataId, strtoull(rsf->AccessControlInfo.ExtSaveDataId,NULL,0), LE);
if (rsf->AccessControlInfo.UseExtSaveData || rsf->AccessControlInfo.ExtSaveDataId) {
if (rsf->AccessControlInfo.ExtSaveDataId)
u64_to_u8(arm11->storageInfo.extSavedataId, strtoull(rsf->AccessControlInfo.ExtSaveDataId, NULL, 0), LE);
else
u32_to_u8(arm11->storageInfo.extSavedataId, GetTidUniqueId(u8_to_u64(arm11->programId,LE)), LE);
}
}
void SetARM11StorageInfoOtherUserSaveData(exhdr_ARM11SystemLocalCapabilities *arm11, rsf_settings *rsf)
@@ -508,6 +540,10 @@ bool CheckCondiditionsForNewAccessibleSaveDataIds(rsf_settings *rsf)
fprintf(stderr,"[EXHEADER ERROR] Too many UniqueId in \"AccessibleSaveDataIds\".\n");
return false;
}
if (rsf->AccessControlInfo.UseExtSaveData) {
fprintf(stderr, "[EXHEADER ERROR] UseExtSaveData must be false if AccessibleSaveDataIds is specified.\n");
return false;
}
if (rsf->AccessControlInfo.ExtSaveDataId){
fprintf(stderr,"[EXHEADER ERROR] ExtSaveDataId is unavailable if AccessibleSaveDataIds is specified.\n");
return false;
@@ -561,8 +597,8 @@ void SetARM11StorageInfoAccessibleSaveDataIds(exhdr_ARM11SystemLocalCapabilities
int SetARM11ServiceAccessControl(exhdr_ARM11SystemLocalCapabilities *arm11, rsf_settings *rsf)
{
if(rsf->AccessControlInfo.ServiceAccessControl){
if(rsf->AccessControlInfo.ServiceAccessControlNum > 32){
fprintf(stderr,"[EXHEADER ERROR] Too Many Service Names, maximum is 32\n");
if(rsf->AccessControlInfo.ServiceAccessControlNum > 34){
fprintf(stderr,"[EXHEADER ERROR] Too Many Service Names, maximum is 34\n");
return EXHDR_BAD_RSF_OPT;
}
for(int i = 0; i < rsf->AccessControlInfo.ServiceAccessControlNum; i++){
+9 -5
View File
@@ -28,6 +28,12 @@ typedef enum
resrc_limit_OTHER
} resource_limit_category;
typedef enum
{
cpuspeed_268MHz,
cpuspeed_804MHz
} cpu_speed;
typedef enum
{
othcap_PERMIT_DEBUG = (1 << 0),
@@ -127,13 +133,11 @@ typedef struct
{
u8 programId[8];
u8 coreVersion[4];
u8 padding0[2];
u8 flag;
u8 priority;
u8 flag[4];
u8 resourceLimitDescriptor[16][2];
exhdr_StorageInfo storageInfo;
u8 serviceAccessControl[32][8]; // Those char[8] server names
u8 padding1[0x1f];
u8 serviceAccessControl[34][8]; // Those char[8] server names
u8 padding1[0xf];
u8 resourceLimitCategory;
} exhdr_ARM11SystemLocalCapabilities;
+273
View File
@@ -0,0 +1,273 @@
<?xml version="1.0" encoding="utf-8"?>
<Project DefaultTargets="Build" ToolsVersion="14.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<ItemGroup Label="ProjectConfigurations">
<ProjectConfiguration Include="Debug|Win32">
<Configuration>Debug</Configuration>
<Platform>Win32</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Release|Win32">
<Configuration>Release</Configuration>
<Platform>Win32</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Debug|x64">
<Configuration>Debug</Configuration>
<Platform>x64</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Release|x64">
<Configuration>Release</Configuration>
<Platform>x64</Platform>
</ProjectConfiguration>
</ItemGroup>
<PropertyGroup Label="Globals">
<ProjectGuid>{21926330-F5A5-4643-AD32-D4F167CE226B}</ProjectGuid>
<Keyword>MakeFileProj</Keyword>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
<ConfigurationType>Makefile</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
<ConfigurationType>Makefile</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
<ImportGroup Label="ExtensionSettings">
</ImportGroup>
<ImportGroup Label="Shared">
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<PropertyGroup Label="UserMacros" />
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<NMakeBuildCommandLine>make</NMakeBuildCommandLine>
<NMakeOutput>makerom.exe</NMakeOutput>
<NMakeCleanCommandLine>make clean</NMakeCleanCommandLine>
<NMakeReBuildCommandLine>make rebuild</NMakeReBuildCommandLine>
<NMakePreprocessorDefinitions>WIN32;_DEBUG;$(NMakePreprocessorDefinitions)</NMakePreprocessorDefinitions>
<IncludePath>C:\Program Files\mingw-w64\x86_64-5.2.0-win32-seh-rt_v4-rev0\mingw64\x86_64-w64-mingw32\include;$(IncludePath)</IncludePath>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<NMakeBuildCommandLine>make</NMakeBuildCommandLine>
<NMakeOutput>makerom.exe</NMakeOutput>
<NMakeCleanCommandLine>make clean</NMakeCleanCommandLine>
<NMakeReBuildCommandLine>make rebuild</NMakeReBuildCommandLine>
<NMakePreprocessorDefinitions>WIN32;NDEBUG;$(NMakePreprocessorDefinitions)</NMakePreprocessorDefinitions>
</PropertyGroup>
<ItemDefinitionGroup>
</ItemDefinitionGroup>
<ItemGroup>
<Text Include="readme.txt" />
</ItemGroup>
<ItemGroup>
<ClInclude Include="accessdesc.h" />
<ClInclude Include="blz.h" />
<ClInclude Include="cardinfo.h" />
<ClInclude Include="certs.h" />
<ClInclude Include="cia.h" />
<ClInclude Include="cia_build.h" />
<ClInclude Include="cia_read.h" />
<ClInclude Include="crr.h" />
<ClInclude Include="crypto.h" />
<ClInclude Include="ctr_utils.h" />
<ClInclude Include="desc\dev_sigdata.h" />
<ClInclude Include="desc\presets.h" />
<ClInclude Include="desc\prod_sigdata.h" />
<ClInclude Include="dir.h" />
<ClInclude Include="elf.h" />
<ClInclude Include="elf_hdr.h" />
<ClInclude Include="exefs.h" />
<ClInclude Include="exefs_build.h" />
<ClInclude Include="exefs_read.h" />
<ClInclude Include="exheader.h" />
<ClInclude Include="exheader_build.h" />
<ClInclude Include="exheader_read.h" />
<ClInclude Include="keyset.h" />
<ClInclude Include="lib.h" />
<ClInclude Include="libyaml\yaml.h" />
<ClInclude Include="libyaml\yaml_private.h" />
<ClInclude Include="ncch.h" />
<ClInclude Include="ncch_build.h" />
<ClInclude Include="ncch_logo.h" />
<ClInclude Include="ncch_read.h" />
<ClInclude Include="ncsd.h" />
<ClInclude Include="ncsd_build.h" />
<ClInclude Include="ncsd_read.h" />
<ClInclude Include="pki\dev.h" />
<ClInclude Include="pki\dev_legacy.h" />
<ClInclude Include="pki\prod.h" />
<ClInclude Include="pki\prod_legacy.h" />
<ClInclude Include="pki\test.h" />
<ClInclude Include="polarssl\aes.h" />
<ClInclude Include="polarssl\arc4.h" />
<ClInclude Include="polarssl\asn1.h" />
<ClInclude Include="polarssl\asn1write.h" />
<ClInclude Include="polarssl\base64.h" />
<ClInclude Include="polarssl\bignum.h" />
<ClInclude Include="polarssl\blowfish.h" />
<ClInclude Include="polarssl\bn_mul.h" />
<ClInclude Include="polarssl\camellia.h" />
<ClInclude Include="polarssl\certs.h" />
<ClInclude Include="polarssl\cipher.h" />
<ClInclude Include="polarssl\cipher_wrap.h" />
<ClInclude Include="polarssl\config.h" />
<ClInclude Include="polarssl\ctr_drbg.h" />
<ClInclude Include="polarssl\debug.h" />
<ClInclude Include="polarssl\des.h" />
<ClInclude Include="polarssl\dhm.h" />
<ClInclude Include="polarssl\entropy.h" />
<ClInclude Include="polarssl\entropy_poll.h" />
<ClInclude Include="polarssl\error.h" />
<ClInclude Include="polarssl\gcm.h" />
<ClInclude Include="polarssl\havege.h" />
<ClInclude Include="polarssl\md.h" />
<ClInclude Include="polarssl\md2.h" />
<ClInclude Include="polarssl\md4.h" />
<ClInclude Include="polarssl\md5.h" />
<ClInclude Include="polarssl\md_wrap.h" />
<ClInclude Include="polarssl\net.h" />
<ClInclude Include="polarssl\openssl.h" />
<ClInclude Include="polarssl\padlock.h" />
<ClInclude Include="polarssl\pbkdf2.h" />
<ClInclude Include="polarssl\pem.h" />
<ClInclude Include="polarssl\pkcs11.h" />
<ClInclude Include="polarssl\pkcs12.h" />
<ClInclude Include="polarssl\pkcs5.h" />
<ClInclude Include="polarssl\rsa.h" />
<ClInclude Include="polarssl\sha1.h" />
<ClInclude Include="polarssl\sha2.h" />
<ClInclude Include="polarssl\sha4.h" />
<ClInclude Include="polarssl\ssl.h" />
<ClInclude Include="polarssl\ssl_cache.h" />
<ClInclude Include="polarssl\timing.h" />
<ClInclude Include="polarssl\version.h" />
<ClInclude Include="polarssl\x509.h" />
<ClInclude Include="polarssl\x509write.h" />
<ClInclude Include="polarssl\xtea.h" />
<ClInclude Include="romfs.h" />
<ClInclude Include="romfs_gen.h" />
<ClInclude Include="romfs_import.h" />
<ClInclude Include="rsf_settings.h" />
<ClInclude Include="srl.h" />
<ClInclude Include="tik.h" />
<ClInclude Include="tik_build.h" />
<ClInclude Include="tik_read.h" />
<ClInclude Include="titleid.h" />
<ClInclude Include="tmd.h" />
<ClInclude Include="tmd_build.h" />
<ClInclude Include="tmd_read.h" />
<ClInclude Include="types.h" />
<ClInclude Include="user_settings.h" />
<ClInclude Include="utf.h" />
<ClInclude Include="utils.h" />
<ClInclude Include="yaml_parser.h" />
</ItemGroup>
<ItemGroup>
<ClCompile Include="accessdesc.c" />
<ClCompile Include="blz.c" />
<ClCompile Include="cardinfo.c" />
<ClCompile Include="certs.c" />
<ClCompile Include="cia.c" />
<ClCompile Include="crypto.c" />
<ClCompile Include="ctr_utils.c" />
<ClCompile Include="dir.c" />
<ClCompile Include="elf.c" />
<ClCompile Include="exefs.c" />
<ClCompile Include="exheader.c" />
<ClCompile Include="keyset.c" />
<ClCompile Include="libyaml\api.c" />
<ClCompile Include="libyaml\dumper.c" />
<ClCompile Include="libyaml\emitter.c" />
<ClCompile Include="libyaml\loader.c" />
<ClCompile Include="libyaml\parser.c" />
<ClCompile Include="libyaml\reader.c" />
<ClCompile Include="libyaml\scanner.c" />
<ClCompile Include="libyaml\writer.c" />
<ClCompile Include="makerom.c" />
<ClCompile Include="ncch.c" />
<ClCompile Include="ncsd.c" />
<ClCompile Include="polarssl\arc4.c" />
<ClCompile Include="polarssl\asn1parse.c" />
<ClCompile Include="polarssl\asn1write.c" />
<ClCompile Include="polarssl\base64.c" />
<ClCompile Include="polarssl\bignum.c" />
<ClCompile Include="polarssl\blowfish.c" />
<ClCompile Include="polarssl\camellia.c" />
<ClCompile Include="polarssl\certs.c" />
<ClCompile Include="polarssl\cipher.c" />
<ClCompile Include="polarssl\cipher_wrap.c" />
<ClCompile Include="polarssl\ctr_drbg.c" />
<ClCompile Include="polarssl\debug.c" />
<ClCompile Include="polarssl\des.c" />
<ClCompile Include="polarssl\dhm.c" />
<ClCompile Include="polarssl\entropy.c" />
<ClCompile Include="polarssl\entropy_poll.c" />
<ClCompile Include="polarssl\error.c" />
<ClCompile Include="polarssl\gcm.c" />
<ClCompile Include="polarssl\havege.c" />
<ClCompile Include="polarssl\md.c" />
<ClCompile Include="polarssl\md2.c" />
<ClCompile Include="polarssl\md4.c" />
<ClCompile Include="polarssl\md5.c" />
<ClCompile Include="polarssl\md_wrap.c" />
<ClCompile Include="polarssl\net.c" />
<ClCompile Include="polarssl\padlock.c" />
<ClCompile Include="polarssl\pbkdf2.c" />
<ClCompile Include="polarssl\pem.c" />
<ClCompile Include="polarssl\pkcs11.c" />
<ClCompile Include="polarssl\pkcs12.c" />
<ClCompile Include="polarssl\pkcs5.c" />
<ClCompile Include="polarssl\rsa.c" />
<ClCompile Include="polarssl\sha1.c" />
<ClCompile Include="polarssl\sha2.c" />
<ClCompile Include="polarssl\sha4.c" />
<ClCompile Include="polarssl\ssl_cache.c" />
<ClCompile Include="polarssl\ssl_cli.c" />
<ClCompile Include="polarssl\ssl_srv.c" />
<ClCompile Include="polarssl\ssl_tls.c" />
<ClCompile Include="polarssl\timing.c" />
<ClCompile Include="polarssl\version.c" />
<ClCompile Include="polarssl\x509parse.c" />
<ClCompile Include="polarssl\x509write.c" />
<ClCompile Include="polarssl\xtea.c" />
<ClCompile Include="romfs.c" />
<ClCompile Include="romfs_gen.c" />
<ClCompile Include="romfs_import.c" />
<ClCompile Include="rsf_settings.c" />
<ClCompile Include="tik.c" />
<ClCompile Include="titleid.c" />
<ClCompile Include="tmd.c" />
<ClCompile Include="user_settings.c" />
<ClCompile Include="utf.c" />
<ClCompile Include="utils.c" />
<ClCompile Include="yaml_parser.c" />
</ItemGroup>
<ItemGroup>
<None Include="Makefile" />
</ItemGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
<ImportGroup Label="ExtensionTargets">
</ImportGroup>
</Project>
+584
View File
@@ -0,0 +1,584 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<ItemGroup>
<Filter Include="Source Files">
<UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
<Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
</Filter>
<Filter Include="Header Files">
<UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
<Extensions>h;hh;hpp;hxx;hm;inl;inc;xsd</Extensions>
</Filter>
<Filter Include="Resource Files">
<UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
<Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
</Filter>
<Filter Include="Header Files\polarssl">
<UniqueIdentifier>{bab0486d-d6e9-48e4-b4a5-ab1c9a917a15}</UniqueIdentifier>
</Filter>
<Filter Include="Header Files\libyaml">
<UniqueIdentifier>{e3b6ff03-546a-4f9c-8246-ee2a5a6b5c20}</UniqueIdentifier>
</Filter>
<Filter Include="Source Files\libyaml">
<UniqueIdentifier>{2bf08da5-c0b2-4b6f-a07a-0f3a03b79f14}</UniqueIdentifier>
</Filter>
<Filter Include="Source Files\polarssl">
<UniqueIdentifier>{7545c89e-a9ce-4c04-989e-ae726a518efd}</UniqueIdentifier>
</Filter>
<Filter Include="Resource Files\PKI">
<UniqueIdentifier>{49964d4d-b429-41e6-a85f-e4d361de0faf}</UniqueIdentifier>
</Filter>
<Filter Include="Resource Files\DESC">
<UniqueIdentifier>{a0455bf4-2a1e-4ced-9d42-88d7ce131c22}</UniqueIdentifier>
</Filter>
</ItemGroup>
<ItemGroup>
<Text Include="readme.txt" />
</ItemGroup>
<ItemGroup>
<ClInclude Include="accessdesc.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="blz.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="cardinfo.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="certs.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="cia.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="cia_build.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="cia_read.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="crr.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="crypto.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="ctr_utils.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="dir.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="elf.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="elf_hdr.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="exefs.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="exefs_build.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="exefs_read.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="exheader.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="exheader_build.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="exheader_read.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="keyset.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="lib.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="ncch.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="ncch_build.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="ncch_logo.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="ncch_read.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="ncsd.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="ncsd_build.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="ncsd_read.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="romfs.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="romfs_gen.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="romfs_import.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="rsf_settings.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="srl.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="tik.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="tik_build.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="tik_read.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="titleid.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="tmd.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="tmd_build.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="tmd_read.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="types.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="user_settings.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="utf.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="utils.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="yaml_parser.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="polarssl\aes.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\arc4.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\asn1.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\asn1write.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\base64.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\bignum.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\blowfish.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\bn_mul.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\camellia.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\certs.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\cipher.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\cipher_wrap.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\config.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\ctr_drbg.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\debug.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\des.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\dhm.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\entropy.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\entropy_poll.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\error.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\gcm.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\havege.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\md.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\md_wrap.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\md2.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\md4.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\md5.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\net.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\openssl.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\padlock.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\pbkdf2.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\pem.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\pkcs5.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\pkcs11.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\pkcs12.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\rsa.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\sha1.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\sha2.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\sha4.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\ssl.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\ssl_cache.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\timing.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\version.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\x509.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\x509write.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="polarssl\xtea.h">
<Filter>Header Files\polarssl</Filter>
</ClInclude>
<ClInclude Include="libyaml\yaml.h">
<Filter>Header Files\libyaml</Filter>
</ClInclude>
<ClInclude Include="libyaml\yaml_private.h">
<Filter>Header Files\libyaml</Filter>
</ClInclude>
<ClInclude Include="pki\dev.h">
<Filter>Resource Files\PKI</Filter>
</ClInclude>
<ClInclude Include="pki\dev_legacy.h">
<Filter>Resource Files\PKI</Filter>
</ClInclude>
<ClInclude Include="pki\prod.h">
<Filter>Resource Files\PKI</Filter>
</ClInclude>
<ClInclude Include="pki\prod_legacy.h">
<Filter>Resource Files\PKI</Filter>
</ClInclude>
<ClInclude Include="pki\test.h">
<Filter>Resource Files\PKI</Filter>
</ClInclude>
<ClInclude Include="desc\dev_sigdata.h">
<Filter>Resource Files\DESC</Filter>
</ClInclude>
<ClInclude Include="desc\presets.h">
<Filter>Resource Files\DESC</Filter>
</ClInclude>
<ClInclude Include="desc\prod_sigdata.h">
<Filter>Resource Files\DESC</Filter>
</ClInclude>
</ItemGroup>
<ItemGroup>
<ClCompile Include="accessdesc.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="blz.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="cardinfo.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="certs.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="cia.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="crypto.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="ctr_utils.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="dir.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="elf.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="exefs.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="exheader.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="keyset.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="makerom.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="ncch.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="ncsd.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="romfs.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="romfs_gen.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="romfs_import.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="rsf_settings.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="tik.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="titleid.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="tmd.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="user_settings.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="utf.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="utils.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="yaml_parser.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="libyaml\api.c">
<Filter>Source Files\libyaml</Filter>
</ClCompile>
<ClCompile Include="libyaml\dumper.c">
<Filter>Source Files\libyaml</Filter>
</ClCompile>
<ClCompile Include="libyaml\emitter.c">
<Filter>Source Files\libyaml</Filter>
</ClCompile>
<ClCompile Include="libyaml\loader.c">
<Filter>Source Files\libyaml</Filter>
</ClCompile>
<ClCompile Include="libyaml\parser.c">
<Filter>Source Files\libyaml</Filter>
</ClCompile>
<ClCompile Include="libyaml\reader.c">
<Filter>Source Files\libyaml</Filter>
</ClCompile>
<ClCompile Include="libyaml\scanner.c">
<Filter>Source Files\libyaml</Filter>
</ClCompile>
<ClCompile Include="libyaml\writer.c">
<Filter>Source Files\libyaml</Filter>
</ClCompile>
<ClCompile Include="polarssl\arc4.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\asn1parse.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\asn1write.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\base64.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\bignum.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\blowfish.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\camellia.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\certs.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\cipher.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\cipher_wrap.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\ctr_drbg.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\debug.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\des.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\dhm.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\entropy.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\entropy_poll.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\error.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\gcm.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\havege.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\md.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\md_wrap.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\md2.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\md4.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\md5.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\net.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\padlock.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\pbkdf2.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\pem.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\pkcs5.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\pkcs11.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\pkcs12.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\rsa.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\sha1.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\sha2.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\sha4.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\ssl_cache.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\ssl_cli.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\ssl_srv.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\ssl_tls.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\timing.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\version.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\x509parse.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\x509write.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
<ClCompile Include="polarssl\xtea.c">
<Filter>Source Files\polarssl</Filter>
</ClCompile>
</ItemGroup>
<ItemGroup>
<None Include="Makefile">
<Filter>Resource Files</Filter>
</None>
</ItemGroup>
</Project>
+32 -12
View File
@@ -626,28 +626,48 @@ int SetCommonHeaderBasicData(ncch_settings *set, ncch_hdr *hdr)
hdr->flags[ncchflag_CONTENT_BLOCK_SIZE] = GetCtrBlockSizeFlag(set->options.blockSize);
/* Setting ContentPlatform */
hdr->flags[ncchflag_CONTENT_PLATFORM] = 1; // CTR
if(set->rsfSet->TitleInfo.Platform){
if(strcasecmp(set->rsfSet->TitleInfo.Platform, "ctr") == 0)
hdr->flags[ncchflag_CONTENT_PLATFORM] = platform_CTR;
else if (strcasecmp(set->rsfSet->TitleInfo.Platform, "snake") == 0)
hdr->flags[ncchflag_CONTENT_PLATFORM] = platform_SNAKE;
else{
fprintf(stderr, "[NCCH ERROR] Invalid Platform '%s'\n", set->rsfSet->TitleInfo.Platform);
return NCCH_BAD_RSF_SET;
}
}
else
hdr->flags[ncchflag_CONTENT_PLATFORM] = platform_CTR;
/* Setting OtherFlag */
if(!set->options.UseRomFS)
hdr->flags[ncchflag_OTHER_FLAG] |= otherflag_NoMountRomFs;
/* Setting FormType */
hdr->flags[ncchflag_CONTENT_TYPE] = form_Unassigned;
if(set->options.IsCfa)
hdr->flags[ncchflag_CONTENT_TYPE] = form_SimpleContent;
else if (set->options.UseRomFS)
hdr->flags[ncchflag_CONTENT_TYPE] = form_Executable;
else
hdr->flags[ncchflag_CONTENT_TYPE] = form_ExecutableWithoutRomfs;
/* Setting ContentType */
hdr->flags[ncchflag_CONTENT_TYPE] = 0;
if(set->options.UseRomFS) hdr->flags[ncchflag_CONTENT_TYPE] |= content_Data;
if(!set->options.IsCfa) hdr->flags[ncchflag_CONTENT_TYPE] |= content_Executable;
if(set->rsfSet->BasicInfo.ContentType){
if(strcmp(set->rsfSet->BasicInfo.ContentType,"Application") == 0) hdr->flags[ncchflag_CONTENT_TYPE] |= 0;
else if(strcmp(set->rsfSet->BasicInfo.ContentType,"SystemUpdate") == 0) hdr->flags[ncchflag_CONTENT_TYPE] |= content_SystemUpdate;
else if(strcmp(set->rsfSet->BasicInfo.ContentType,"Manual") == 0) hdr->flags[ncchflag_CONTENT_TYPE] |= content_Manual;
else if(strcmp(set->rsfSet->BasicInfo.ContentType,"Child") == 0) hdr->flags[ncchflag_CONTENT_TYPE] |= content_Child;
else if(strcmp(set->rsfSet->BasicInfo.ContentType,"Trial") == 0) hdr->flags[ncchflag_CONTENT_TYPE] |= content_Trial;
if(strcmp(set->rsfSet->BasicInfo.ContentType,"Application") == 0) hdr->flags[ncchflag_CONTENT_TYPE] |= (content_Application << 2);
else if(strcmp(set->rsfSet->BasicInfo.ContentType,"SystemUpdate") == 0) hdr->flags[ncchflag_CONTENT_TYPE] |= (content_SystemUpdate << 2);
else if(strcmp(set->rsfSet->BasicInfo.ContentType,"Manual") == 0) hdr->flags[ncchflag_CONTENT_TYPE] |= (content_Manual << 2);
else if(strcmp(set->rsfSet->BasicInfo.ContentType,"Child") == 0) hdr->flags[ncchflag_CONTENT_TYPE] |= (content_Child << 2);
else if(strcmp(set->rsfSet->BasicInfo.ContentType,"Trial") == 0) hdr->flags[ncchflag_CONTENT_TYPE] |= (content_Trial << 2);
else if (strcmp(set->rsfSet->BasicInfo.ContentType, "ExtendedSystemUpdate") == 0) hdr->flags[ncchflag_CONTENT_TYPE] |= (content_ExtendedSystemUpdate << 2);
else{
fprintf(stderr,"[NCCH ERROR] Invalid ContentType '%s'\n",set->rsfSet->BasicInfo.ContentType);
return NCCH_BAD_RSF_SET;
}
}
else
hdr->flags[ncchflag_CONTENT_TYPE] |= (content_Application << 2);
return 0;
}
@@ -663,7 +683,7 @@ bool IsValidProductCode(char *ProductCode, bool FreeProductCode)
if(strlen(ProductCode) < 10)
return false;
if(strncmp(ProductCode,"CTR",3) != 0)
if(strncmp(ProductCode,"CTR",3) != 0 && strncmp(ProductCode, "KTR", 3) != 0)
return false;
for(int i = 3; i < 10; i++){
@@ -946,12 +966,12 @@ bool IsNcch(FILE *fp, u8 *buf)
bool IsCfa(ncch_hdr* hdr)
{
return (((hdr->flags[ncchflag_CONTENT_TYPE] & content_Data) == content_Data) && ((hdr->flags[ncchflag_CONTENT_TYPE] & content_Executable) != content_Executable));
return (hdr->flags[ncchflag_CONTENT_TYPE] & 3) == form_SimpleContent;
}
bool IsUpdateCfa(ncch_hdr* hdr)
{
return (((hdr->flags[ncchflag_CONTENT_TYPE] & content_SystemUpdate) == content_SystemUpdate) && ((hdr->flags[ncchflag_CONTENT_TYPE] & content_Child) != content_Child) && IsCfa(hdr));
return (hdr->flags[ncchflag_CONTENT_TYPE] >> 2) == content_SystemUpdate || (hdr->flags[ncchflag_CONTENT_TYPE] >> 2) == content_ExtendedSystemUpdate;
}
u32 GetNcchBlockSize(ncch_hdr* hdr)
+20 -6
View File
@@ -50,14 +50,28 @@ typedef enum
typedef enum
{
content_Data = 0x1,
content_Executable = 0x2,
content_SystemUpdate = 0x4,
content_Manual = 0x8,
content_Child = (0x4|0x8),
content_Trial = 0x10
form_Unassigned,
form_SimpleContent,
form_ExecutableWithoutRomfs,
form_Executable
} ncch_form_type;
typedef enum
{
content_Application,
content_SystemUpdate,
content_Manual,
content_Child,
content_Trial,
content_ExtendedSystemUpdate
} ncch_content_bitmask;
typedef enum
{
platform_CTR = 0x1,
platform_SNAKE = 0x2
} ncch_platform;
typedef struct
{
u16 formatVersion;
-173
View File
@@ -1,173 +0,0 @@
/*
* An implementation of the ARCFOUR algorithm
*
* Copyright (C) 2006-2013, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*
* The ARCFOUR algorithm was publicly disclosed on 94/09.
*
* http://groups.google.com/group/sci.crypt/msg/10a300c9d21afca0
*/
#include "polarssl/config.h"
#if defined(POLARSSL_ARC4_C)
#include "polarssl/arc4.h"
#if !defined(POLARSSL_ARC4_ALT)
/*
* ARC4 key schedule
*/
void arc4_setup( arc4_context *ctx, const unsigned char *key, unsigned int keylen )
{
int i, j, a;
unsigned int k;
unsigned char *m;
ctx->x = 0;
ctx->y = 0;
m = ctx->m;
for( i = 0; i < 256; i++ )
m[i] = (unsigned char) i;
j = k = 0;
for( i = 0; i < 256; i++, k++ )
{
if( k >= keylen ) k = 0;
a = m[i];
j = ( j + a + key[k] ) & 0xFF;
m[i] = m[j];
m[j] = (unsigned char) a;
}
}
/*
* ARC4 cipher function
*/
int arc4_crypt( arc4_context *ctx, size_t length, const unsigned char *input,
unsigned char *output )
{
int x, y, a, b;
size_t i;
unsigned char *m;
x = ctx->x;
y = ctx->y;
m = ctx->m;
for( i = 0; i < length; i++ )
{
x = ( x + 1 ) & 0xFF; a = m[x];
y = ( y + a ) & 0xFF; b = m[y];
m[x] = (unsigned char) b;
m[y] = (unsigned char) a;
output[i] = (unsigned char)
( input[i] ^ m[(unsigned char)( a + b )] );
}
ctx->x = x;
ctx->y = y;
return( 0 );
}
#endif /* !POLARSSL_ARC4_ALT */
#if defined(POLARSSL_SELF_TEST)
#include <string.h>
#include <stdio.h>
/*
* ARC4 tests vectors as posted by Eric Rescorla in sep. 1994:
*
* http://groups.google.com/group/comp.security.misc/msg/10a300c9d21afca0
*/
static const unsigned char arc4_test_key[3][8] =
{
{ 0x01, 0x23, 0x45, 0x67, 0x89, 0xAB, 0xCD, 0xEF },
{ 0x01, 0x23, 0x45, 0x67, 0x89, 0xAB, 0xCD, 0xEF },
{ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }
};
static const unsigned char arc4_test_pt[3][8] =
{
{ 0x01, 0x23, 0x45, 0x67, 0x89, 0xAB, 0xCD, 0xEF },
{ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
{ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }
};
static const unsigned char arc4_test_ct[3][8] =
{
{ 0x75, 0xB7, 0x87, 0x80, 0x99, 0xE0, 0xC5, 0x96 },
{ 0x74, 0x94, 0xC2, 0xE7, 0x10, 0x4B, 0x08, 0x79 },
{ 0xDE, 0x18, 0x89, 0x41, 0xA3, 0x37, 0x5D, 0x3A }
};
/*
* Checkup routine
*/
int arc4_self_test( int verbose )
{
int i;
unsigned char ibuf[8];
unsigned char obuf[8];
arc4_context ctx;
for( i = 0; i < 3; i++ )
{
if( verbose != 0 )
printf( " ARC4 test #%d: ", i + 1 );
memcpy( ibuf, arc4_test_pt[i], 8 );
arc4_setup( &ctx, arc4_test_key[i], 8 );
arc4_crypt( &ctx, 8, ibuf, obuf );
if( memcmp( obuf, arc4_test_ct[i], 8 ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( verbose != 0 )
printf( "passed\n" );
}
if( verbose != 0 )
printf( "\n" );
return( 0 );
}
#endif
#endif
-260
View File
@@ -1,260 +0,0 @@
/*
* Generic ASN.1 parsing
*
* Copyright (C) 2006-2011, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_ASN1_PARSE_C)
#include "polarssl/asn1.h"
#if defined(POLARSSL_BIGNUM_C)
#include "polarssl/bignum.h"
#endif
#include <string.h>
#include <stdlib.h>
#include <time.h>
/*
* ASN.1 DER decoding routines
*/
int asn1_get_len( unsigned char **p,
const unsigned char *end,
size_t *len )
{
if( ( end - *p ) < 1 )
return( POLARSSL_ERR_ASN1_OUT_OF_DATA );
if( ( **p & 0x80 ) == 0 )
*len = *(*p)++;
else
{
switch( **p & 0x7F )
{
case 1:
if( ( end - *p ) < 2 )
return( POLARSSL_ERR_ASN1_OUT_OF_DATA );
*len = (*p)[1];
(*p) += 2;
break;
case 2:
if( ( end - *p ) < 3 )
return( POLARSSL_ERR_ASN1_OUT_OF_DATA );
*len = ( (*p)[1] << 8 ) | (*p)[2];
(*p) += 3;
break;
case 3:
if( ( end - *p ) < 4 )
return( POLARSSL_ERR_ASN1_OUT_OF_DATA );
*len = ( (*p)[1] << 16 ) | ( (*p)[2] << 8 ) | (*p)[3];
(*p) += 4;
break;
case 4:
if( ( end - *p ) < 5 )
return( POLARSSL_ERR_ASN1_OUT_OF_DATA );
*len = ( (*p)[1] << 24 ) | ( (*p)[2] << 16 ) | ( (*p)[3] << 8 ) | (*p)[4];
(*p) += 5;
break;
default:
return( POLARSSL_ERR_ASN1_INVALID_LENGTH );
}
}
if( *len > (size_t) ( end - *p ) )
return( POLARSSL_ERR_ASN1_OUT_OF_DATA );
return( 0 );
}
int asn1_get_tag( unsigned char **p,
const unsigned char *end,
size_t *len, int tag )
{
if( ( end - *p ) < 1 )
return( POLARSSL_ERR_ASN1_OUT_OF_DATA );
if( **p != tag )
return( POLARSSL_ERR_ASN1_UNEXPECTED_TAG );
(*p)++;
return( asn1_get_len( p, end, len ) );
}
int asn1_get_bool( unsigned char **p,
const unsigned char *end,
int *val )
{
int ret;
size_t len;
if( ( ret = asn1_get_tag( p, end, &len, ASN1_BOOLEAN ) ) != 0 )
return( ret );
if( len != 1 )
return( POLARSSL_ERR_ASN1_INVALID_LENGTH );
*val = ( **p != 0 ) ? 1 : 0;
(*p)++;
return( 0 );
}
int asn1_get_int( unsigned char **p,
const unsigned char *end,
int *val )
{
int ret;
size_t len;
if( ( ret = asn1_get_tag( p, end, &len, ASN1_INTEGER ) ) != 0 )
return( ret );
if( len > sizeof( int ) || ( **p & 0x80 ) != 0 )
return( POLARSSL_ERR_ASN1_INVALID_LENGTH );
*val = 0;
while( len-- > 0 )
{
*val = ( *val << 8 ) | **p;
(*p)++;
}
return( 0 );
}
#if defined(POLARSSL_BIGNUM_C)
int asn1_get_mpi( unsigned char **p,
const unsigned char *end,
mpi *X )
{
int ret;
size_t len;
if( ( ret = asn1_get_tag( p, end, &len, ASN1_INTEGER ) ) != 0 )
return( ret );
ret = mpi_read_binary( X, *p, len );
*p += len;
return( ret );
}
#endif /* POLARSSL_BIGNUM_C */
int asn1_get_bitstring( unsigned char **p, const unsigned char *end,
asn1_bitstring *bs)
{
int ret;
/* Certificate type is a single byte bitstring */
if( ( ret = asn1_get_tag( p, end, &bs->len, ASN1_BIT_STRING ) ) != 0 )
return( ret );
/* Check length, subtract one for actual bit string length */
if ( bs->len < 1 )
return( POLARSSL_ERR_ASN1_OUT_OF_DATA );
bs->len -= 1;
/* Get number of unused bits, ensure unused bits <= 7 */
bs->unused_bits = **p;
if( bs->unused_bits > 7 )
return( POLARSSL_ERR_ASN1_INVALID_LENGTH );
(*p)++;
/* Get actual bitstring */
bs->p = *p;
*p += bs->len;
if( *p != end )
return( POLARSSL_ERR_ASN1_LENGTH_MISMATCH );
return 0;
}
/*
* Parses and splits an ASN.1 "SEQUENCE OF <tag>"
*/
int asn1_get_sequence_of( unsigned char **p,
const unsigned char *end,
asn1_sequence *cur,
int tag)
{
int ret;
size_t len;
asn1_buf *buf;
/* Get main sequence tag */
if( ( ret = asn1_get_tag( p, end, &len,
ASN1_CONSTRUCTED | ASN1_SEQUENCE ) ) != 0 )
return( ret );
if( *p + len != end )
return( POLARSSL_ERR_ASN1_LENGTH_MISMATCH );
while( *p < end )
{
buf = &(cur->buf);
buf->tag = **p;
if( ( ret = asn1_get_tag( p, end, &buf->len, tag ) ) != 0 )
return( ret );
buf->p = *p;
*p += buf->len;
/* Allocate and assign next pointer */
if (*p < end)
{
cur->next = (asn1_sequence *) malloc(
sizeof( asn1_sequence ) );
if( cur->next == NULL )
return( POLARSSL_ERR_ASN1_MALLOC_FAILED );
cur = cur->next;
}
}
/* Set final sequence entry's next pointer to NULL */
cur->next = NULL;
if( *p != end )
return( POLARSSL_ERR_ASN1_LENGTH_MISMATCH );
return( 0 );
}
#endif
-241
View File
@@ -1,241 +0,0 @@
/*
* ASN.1 buffer writing functionality
*
* Copyright (C) 2006-2012, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_ASN1_WRITE_C)
#include "polarssl/asn1write.h"
int asn1_write_len( unsigned char **p, unsigned char *start, size_t len )
{
if( len < 0x80 )
{
if( *p - start < 1 )
return( POLARSSL_ERR_ASN1_BUF_TOO_SMALL );
*--(*p) = len;
return( 1 );
}
if( len <= 0xFF )
{
if( *p - start < 2 )
return( POLARSSL_ERR_ASN1_BUF_TOO_SMALL );
*--(*p) = len;
*--(*p) = 0x81;
return( 2 );
}
if( *p - start < 3 )
return( POLARSSL_ERR_ASN1_BUF_TOO_SMALL );
// We assume we never have lengths larger than 65535 bytes
//
*--(*p) = len % 256;
*--(*p) = ( len / 256 ) % 256;
*--(*p) = 0x82;
return( 3 );
}
int asn1_write_tag( unsigned char **p, unsigned char *start, unsigned char tag )
{
if( *p - start < 1 )
return( POLARSSL_ERR_ASN1_BUF_TOO_SMALL );
*--(*p) = tag;
return( 1 );
}
int asn1_write_mpi( unsigned char **p, unsigned char *start, mpi *X )
{
int ret;
size_t len = 0;
// Write the MPI
//
len = mpi_size( X );
if( *p - start < (int) len )
return( POLARSSL_ERR_ASN1_BUF_TOO_SMALL );
(*p) -= len;
mpi_write_binary( X, *p, len );
// DER format assumes 2s complement for numbers, so the leftmost bit
// should be 0 for positive numbers and 1 for negative numbers.
//
if ( X->s ==1 && **p & 0x80 )
{
if( *p - start < 1 )
return( POLARSSL_ERR_ASN1_BUF_TOO_SMALL );
*--(*p) = 0x00;
len += 1;
}
ASN1_CHK_ADD( len, asn1_write_len( p, start, len ) );
ASN1_CHK_ADD( len, asn1_write_tag( p, start, ASN1_INTEGER ) );
return( len );
}
int asn1_write_null( unsigned char **p, unsigned char *start )
{
int ret;
size_t len = 0;
// Write NULL
//
ASN1_CHK_ADD( len, asn1_write_len( p, start, 0) );
ASN1_CHK_ADD( len, asn1_write_tag( p, start, ASN1_NULL ) );
return( len );
}
int asn1_write_oid( unsigned char **p, unsigned char *start, char *oid )
{
int ret;
size_t len = 0;
// Write OID
//
len = strlen( oid );
if( *p - start < (int) len )
return( POLARSSL_ERR_ASN1_BUF_TOO_SMALL );
(*p) -= len;
memcpy( *p, oid, len );
ASN1_CHK_ADD( len , asn1_write_len( p, start, len ) );
ASN1_CHK_ADD( len , asn1_write_tag( p, start, ASN1_OID ) );
return( len );
}
int asn1_write_algorithm_identifier( unsigned char **p, unsigned char *start,
char *algorithm_oid )
{
int ret;
size_t null_len = 0;
size_t oid_len = 0;
size_t len = 0;
// Write NULL
//
ASN1_CHK_ADD( null_len, asn1_write_null( p, start ) );
// Write OID
//
ASN1_CHK_ADD( oid_len, asn1_write_oid( p, start, algorithm_oid ) );
len = oid_len + null_len;
ASN1_CHK_ADD( len, asn1_write_len( p, start, oid_len + null_len ) );
ASN1_CHK_ADD( len, asn1_write_tag( p, start,
ASN1_CONSTRUCTED | ASN1_SEQUENCE ) );
return( len );
}
int asn1_write_int( unsigned char **p, unsigned char *start, int val )
{
int ret;
size_t len = 0;
// TODO negative values and values larger than 128
// DER format assumes 2s complement for numbers, so the leftmost bit
// should be 0 for positive numbers and 1 for negative numbers.
//
if( *p - start < 1 )
return( POLARSSL_ERR_ASN1_BUF_TOO_SMALL );
len += 1;
*--(*p) = val;
if ( val > 0 && **p & 0x80 )
{
if( *p - start < 1 )
return( POLARSSL_ERR_ASN1_BUF_TOO_SMALL );
*--(*p) = 0x00;
len += 1;
}
ASN1_CHK_ADD( len, asn1_write_len( p, start, len ) );
ASN1_CHK_ADD( len, asn1_write_tag( p, start, ASN1_INTEGER ) );
return( len );
}
int asn1_write_printable_string( unsigned char **p, unsigned char *start,
char *text )
{
int ret;
size_t len = 0;
// Write string
//
len = strlen( text );
if( *p - start < (int) len )
return( POLARSSL_ERR_ASN1_BUF_TOO_SMALL );
(*p) -= len;
memcpy( *p, text, len );
ASN1_CHK_ADD( len, asn1_write_len( p, start, len ) );
ASN1_CHK_ADD( len, asn1_write_tag( p, start, ASN1_PRINTABLE_STRING ) );
return( len );
}
int asn1_write_ia5_string( unsigned char **p, unsigned char *start,
char *text )
{
int ret;
size_t len = 0;
// Write string
//
len = strlen( text );
if( *p - start < (int) len )
return( POLARSSL_ERR_ASN1_BUF_TOO_SMALL );
(*p) -= len;
memcpy( *p, text, len );
ASN1_CHK_ADD( len, asn1_write_len( p, start, len ) );
ASN1_CHK_ADD( len, asn1_write_tag( p, start, ASN1_IA5_STRING ) );
return( len );
}
#endif
-632
View File
@@ -1,632 +0,0 @@
/*
* Blowfish implementation
*
* Copyright (C) 2012-2013, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*
* The Blowfish block cipher was designed by Bruce Schneier in 1993.
* http://www.schneier.com/blowfish.html
* http://en.wikipedia.org/wiki/Blowfish_%28cipher%29
*
*/
#include "polarssl/config.h"
#if defined(POLARSSL_BLOWFISH_C)
#include "polarssl/blowfish.h"
#if !defined(POLARSSL_BLOWFISH_ALT)
/*
* 32-bit integer manipulation macros (big endian)
*/
#ifndef GET_UINT32_BE
#define GET_UINT32_BE(n,b,i) \
{ \
(n) = ( (uint32_t) (b)[(i) ] << 24 ) \
| ( (uint32_t) (b)[(i) + 1] << 16 ) \
| ( (uint32_t) (b)[(i) + 2] << 8 ) \
| ( (uint32_t) (b)[(i) + 3] ); \
}
#endif
#ifndef PUT_UINT32_BE
#define PUT_UINT32_BE(n,b,i) \
{ \
(b)[(i) ] = (unsigned char) ( (n) >> 24 ); \
(b)[(i) + 1] = (unsigned char) ( (n) >> 16 ); \
(b)[(i) + 2] = (unsigned char) ( (n) >> 8 ); \
(b)[(i) + 3] = (unsigned char) ( (n) ); \
}
#endif
static const uint32_t P[BLOWFISH_ROUNDS + 2] = {
0x243F6A88L, 0x85A308D3L, 0x13198A2EL, 0x03707344L,
0xA4093822L, 0x299F31D0L, 0x082EFA98L, 0xEC4E6C89L,
0x452821E6L, 0x38D01377L, 0xBE5466CFL, 0x34E90C6CL,
0xC0AC29B7L, 0xC97C50DDL, 0x3F84D5B5L, 0xB5470917L,
0x9216D5D9L, 0x8979FB1BL
};
/* declarations of data at the end of this file */
static const uint32_t S[4][256];
static uint32_t F(blowfish_context *ctx, uint32_t x)
{
unsigned short a, b, c, d;
uint32_t y;
d = (unsigned short)(x & 0xFF);
x >>= 8;
c = (unsigned short)(x & 0xFF);
x >>= 8;
b = (unsigned short)(x & 0xFF);
x >>= 8;
a = (unsigned short)(x & 0xFF);
y = ctx->S[0][a] + ctx->S[1][b];
y = y ^ ctx->S[2][c];
y = y + ctx->S[3][d];
return y;
}
static void blowfish_enc(blowfish_context *ctx, uint32_t *xl, uint32_t *xr)
{
uint32_t Xl, Xr, temp;
short i;
Xl = *xl;
Xr = *xr;
for (i = 0; i < BLOWFISH_ROUNDS; ++i)
{
Xl = Xl ^ ctx->P[i];
Xr = F(ctx, Xl) ^ Xr;
temp = Xl;
Xl = Xr;
Xr = temp;
}
temp = Xl;
Xl = Xr;
Xr = temp;
Xr = Xr ^ ctx->P[BLOWFISH_ROUNDS];
Xl = Xl ^ ctx->P[BLOWFISH_ROUNDS + 1];
*xl = Xl;
*xr = Xr;
}
static void blowfish_dec(blowfish_context *ctx, uint32_t *xl, uint32_t *xr)
{
uint32_t Xl, Xr, temp;
short i;
Xl = *xl;
Xr = *xr;
for (i = BLOWFISH_ROUNDS + 1; i > 1; --i)
{
Xl = Xl ^ ctx->P[i];
Xr = F(ctx, Xl) ^ Xr;
temp = Xl;
Xl = Xr;
Xr = temp;
}
temp = Xl;
Xl = Xr;
Xr = temp;
Xr = Xr ^ ctx->P[1];
Xl = Xl ^ ctx->P[0];
*xl = Xl;
*xr = Xr;
}
/*
* Blowfish key schedule
*/
int blowfish_setkey( blowfish_context *ctx, const unsigned char *key, unsigned int keysize )
{
unsigned int i, j, k;
uint32_t data, datal, datar;
if( keysize < BLOWFISH_MIN_KEY || keysize > BLOWFISH_MAX_KEY ||
( keysize % 8 ) )
{
return POLARSSL_ERR_BLOWFISH_INVALID_KEY_LENGTH;
}
keysize >>= 3;
for( i = 0; i < 4; i++ )
{
for( j = 0; j < 256; j++ )
ctx->S[i][j] = S[i][j];
}
j = 0;
for( i = 0; i < BLOWFISH_ROUNDS + 2; ++i )
{
data = 0x00000000;
for( k = 0; k < 4; ++k )
{
data = ( data << 8 ) | key[j++];
if( j >= keysize )
j = 0;
}
ctx->P[i] = P[i] ^ data;
}
datal = 0x00000000;
datar = 0x00000000;
for( i = 0; i < BLOWFISH_ROUNDS + 2; i += 2 )
{
blowfish_enc( ctx, &datal, &datar );
ctx->P[i] = datal;
ctx->P[i + 1] = datar;
}
for( i = 0; i < 4; i++ )
{
for( j = 0; j < 256; j += 2 )
{
blowfish_enc( ctx, &datal, &datar );
ctx->S[i][j] = datal;
ctx->S[i][j + 1] = datar;
}
}
return( 0 );
}
/*
* Blowfish-ECB block encryption/decryption
*/
int blowfish_crypt_ecb( blowfish_context *ctx,
int mode,
const unsigned char input[BLOWFISH_BLOCKSIZE],
unsigned char output[BLOWFISH_BLOCKSIZE] )
{
uint32_t X0, X1;
GET_UINT32_BE( X0, input, 0 );
GET_UINT32_BE( X1, input, 4 );
if( mode == BLOWFISH_DECRYPT )
{
blowfish_dec(ctx, &X0, &X1);
}
else /* BLOWFISH_ENCRYPT */
{
blowfish_enc(ctx, &X0, &X1);
}
PUT_UINT32_BE( X0, output, 0 );
PUT_UINT32_BE( X1, output, 4 );
return( 0 );
}
/*
* Blowfish-CBC buffer encryption/decryption
*/
int blowfish_crypt_cbc( blowfish_context *ctx,
int mode,
size_t length,
unsigned char iv[BLOWFISH_BLOCKSIZE],
const unsigned char *input,
unsigned char *output )
{
int i;
unsigned char temp[BLOWFISH_BLOCKSIZE];
if( length % BLOWFISH_BLOCKSIZE )
return( POLARSSL_ERR_BLOWFISH_INVALID_INPUT_LENGTH );
if( mode == BLOWFISH_DECRYPT )
{
while( length > 0 )
{
memcpy( temp, input, BLOWFISH_BLOCKSIZE );
blowfish_crypt_ecb( ctx, mode, input, output );
for( i = 0; i < BLOWFISH_BLOCKSIZE;i++ )
output[i] = (unsigned char)( output[i] ^ iv[i] );
memcpy( iv, temp, BLOWFISH_BLOCKSIZE );
input += BLOWFISH_BLOCKSIZE;
output += BLOWFISH_BLOCKSIZE;
length -= BLOWFISH_BLOCKSIZE;
}
}
else
{
while( length > 0 )
{
for( i = 0; i < BLOWFISH_BLOCKSIZE; i++ )
output[i] = (unsigned char)( input[i] ^ iv[i] );
blowfish_crypt_ecb( ctx, mode, output, output );
memcpy( iv, output, BLOWFISH_BLOCKSIZE );
input += BLOWFISH_BLOCKSIZE;
output += BLOWFISH_BLOCKSIZE;
length -= BLOWFISH_BLOCKSIZE;
}
}
return( 0 );
}
#if defined(POLARSSL_CIPHER_MODE_CFB)
/*
* Blowfish CFB buffer encryption/decryption
*/
int blowfish_crypt_cfb64( blowfish_context *ctx,
int mode,
size_t length,
size_t *iv_off,
unsigned char iv[BLOWFISH_BLOCKSIZE],
const unsigned char *input,
unsigned char *output )
{
int c;
size_t n = *iv_off;
if( mode == BLOWFISH_DECRYPT )
{
while( length-- )
{
if( n == 0 )
blowfish_crypt_ecb( ctx, BLOWFISH_ENCRYPT, iv, iv );
c = *input++;
*output++ = (unsigned char)( c ^ iv[n] );
iv[n] = (unsigned char) c;
n = (n + 1) % BLOWFISH_BLOCKSIZE;
}
}
else
{
while( length-- )
{
if( n == 0 )
blowfish_crypt_ecb( ctx, BLOWFISH_ENCRYPT, iv, iv );
iv[n] = *output++ = (unsigned char)( iv[n] ^ *input++ );
n = (n + 1) % BLOWFISH_BLOCKSIZE;
}
}
*iv_off = n;
return( 0 );
}
#endif /*POLARSSL_CIPHER_MODE_CFB */
#if defined(POLARSSL_CIPHER_MODE_CTR)
/*
* Blowfish CTR buffer encryption/decryption
*/
int blowfish_crypt_ctr( blowfish_context *ctx,
size_t length,
size_t *nc_off,
unsigned char nonce_counter[BLOWFISH_BLOCKSIZE],
unsigned char stream_block[BLOWFISH_BLOCKSIZE],
const unsigned char *input,
unsigned char *output )
{
int c, i;
size_t n = *nc_off;
while( length-- )
{
if( n == 0 ) {
blowfish_crypt_ecb( ctx, BLOWFISH_ENCRYPT, nonce_counter, stream_block );
for( i = BLOWFISH_BLOCKSIZE; i > 0; i-- )
if( ++nonce_counter[i - 1] != 0 )
break;
}
c = *input++;
*output++ = (unsigned char)( c ^ stream_block[n] );
n = (n + 1) % BLOWFISH_BLOCKSIZE;
}
*nc_off = n;
return( 0 );
}
#endif /* POLARSSL_CIPHER_MODE_CTR */
static const uint32_t S[4][256] = {
{ 0xD1310BA6L, 0x98DFB5ACL, 0x2FFD72DBL, 0xD01ADFB7L,
0xB8E1AFEDL, 0x6A267E96L, 0xBA7C9045L, 0xF12C7F99L,
0x24A19947L, 0xB3916CF7L, 0x0801F2E2L, 0x858EFC16L,
0x636920D8L, 0x71574E69L, 0xA458FEA3L, 0xF4933D7EL,
0x0D95748FL, 0x728EB658L, 0x718BCD58L, 0x82154AEEL,
0x7B54A41DL, 0xC25A59B5L, 0x9C30D539L, 0x2AF26013L,
0xC5D1B023L, 0x286085F0L, 0xCA417918L, 0xB8DB38EFL,
0x8E79DCB0L, 0x603A180EL, 0x6C9E0E8BL, 0xB01E8A3EL,
0xD71577C1L, 0xBD314B27L, 0x78AF2FDAL, 0x55605C60L,
0xE65525F3L, 0xAA55AB94L, 0x57489862L, 0x63E81440L,
0x55CA396AL, 0x2AAB10B6L, 0xB4CC5C34L, 0x1141E8CEL,
0xA15486AFL, 0x7C72E993L, 0xB3EE1411L, 0x636FBC2AL,
0x2BA9C55DL, 0x741831F6L, 0xCE5C3E16L, 0x9B87931EL,
0xAFD6BA33L, 0x6C24CF5CL, 0x7A325381L, 0x28958677L,
0x3B8F4898L, 0x6B4BB9AFL, 0xC4BFE81BL, 0x66282193L,
0x61D809CCL, 0xFB21A991L, 0x487CAC60L, 0x5DEC8032L,
0xEF845D5DL, 0xE98575B1L, 0xDC262302L, 0xEB651B88L,
0x23893E81L, 0xD396ACC5L, 0x0F6D6FF3L, 0x83F44239L,
0x2E0B4482L, 0xA4842004L, 0x69C8F04AL, 0x9E1F9B5EL,
0x21C66842L, 0xF6E96C9AL, 0x670C9C61L, 0xABD388F0L,
0x6A51A0D2L, 0xD8542F68L, 0x960FA728L, 0xAB5133A3L,
0x6EEF0B6CL, 0x137A3BE4L, 0xBA3BF050L, 0x7EFB2A98L,
0xA1F1651DL, 0x39AF0176L, 0x66CA593EL, 0x82430E88L,
0x8CEE8619L, 0x456F9FB4L, 0x7D84A5C3L, 0x3B8B5EBEL,
0xE06F75D8L, 0x85C12073L, 0x401A449FL, 0x56C16AA6L,
0x4ED3AA62L, 0x363F7706L, 0x1BFEDF72L, 0x429B023DL,
0x37D0D724L, 0xD00A1248L, 0xDB0FEAD3L, 0x49F1C09BL,
0x075372C9L, 0x80991B7BL, 0x25D479D8L, 0xF6E8DEF7L,
0xE3FE501AL, 0xB6794C3BL, 0x976CE0BDL, 0x04C006BAL,
0xC1A94FB6L, 0x409F60C4L, 0x5E5C9EC2L, 0x196A2463L,
0x68FB6FAFL, 0x3E6C53B5L, 0x1339B2EBL, 0x3B52EC6FL,
0x6DFC511FL, 0x9B30952CL, 0xCC814544L, 0xAF5EBD09L,
0xBEE3D004L, 0xDE334AFDL, 0x660F2807L, 0x192E4BB3L,
0xC0CBA857L, 0x45C8740FL, 0xD20B5F39L, 0xB9D3FBDBL,
0x5579C0BDL, 0x1A60320AL, 0xD6A100C6L, 0x402C7279L,
0x679F25FEL, 0xFB1FA3CCL, 0x8EA5E9F8L, 0xDB3222F8L,
0x3C7516DFL, 0xFD616B15L, 0x2F501EC8L, 0xAD0552ABL,
0x323DB5FAL, 0xFD238760L, 0x53317B48L, 0x3E00DF82L,
0x9E5C57BBL, 0xCA6F8CA0L, 0x1A87562EL, 0xDF1769DBL,
0xD542A8F6L, 0x287EFFC3L, 0xAC6732C6L, 0x8C4F5573L,
0x695B27B0L, 0xBBCA58C8L, 0xE1FFA35DL, 0xB8F011A0L,
0x10FA3D98L, 0xFD2183B8L, 0x4AFCB56CL, 0x2DD1D35BL,
0x9A53E479L, 0xB6F84565L, 0xD28E49BCL, 0x4BFB9790L,
0xE1DDF2DAL, 0xA4CB7E33L, 0x62FB1341L, 0xCEE4C6E8L,
0xEF20CADAL, 0x36774C01L, 0xD07E9EFEL, 0x2BF11FB4L,
0x95DBDA4DL, 0xAE909198L, 0xEAAD8E71L, 0x6B93D5A0L,
0xD08ED1D0L, 0xAFC725E0L, 0x8E3C5B2FL, 0x8E7594B7L,
0x8FF6E2FBL, 0xF2122B64L, 0x8888B812L, 0x900DF01CL,
0x4FAD5EA0L, 0x688FC31CL, 0xD1CFF191L, 0xB3A8C1ADL,
0x2F2F2218L, 0xBE0E1777L, 0xEA752DFEL, 0x8B021FA1L,
0xE5A0CC0FL, 0xB56F74E8L, 0x18ACF3D6L, 0xCE89E299L,
0xB4A84FE0L, 0xFD13E0B7L, 0x7CC43B81L, 0xD2ADA8D9L,
0x165FA266L, 0x80957705L, 0x93CC7314L, 0x211A1477L,
0xE6AD2065L, 0x77B5FA86L, 0xC75442F5L, 0xFB9D35CFL,
0xEBCDAF0CL, 0x7B3E89A0L, 0xD6411BD3L, 0xAE1E7E49L,
0x00250E2DL, 0x2071B35EL, 0x226800BBL, 0x57B8E0AFL,
0x2464369BL, 0xF009B91EL, 0x5563911DL, 0x59DFA6AAL,
0x78C14389L, 0xD95A537FL, 0x207D5BA2L, 0x02E5B9C5L,
0x83260376L, 0x6295CFA9L, 0x11C81968L, 0x4E734A41L,
0xB3472DCAL, 0x7B14A94AL, 0x1B510052L, 0x9A532915L,
0xD60F573FL, 0xBC9BC6E4L, 0x2B60A476L, 0x81E67400L,
0x08BA6FB5L, 0x571BE91FL, 0xF296EC6BL, 0x2A0DD915L,
0xB6636521L, 0xE7B9F9B6L, 0xFF34052EL, 0xC5855664L,
0x53B02D5DL, 0xA99F8FA1L, 0x08BA4799L, 0x6E85076AL },
{ 0x4B7A70E9L, 0xB5B32944L, 0xDB75092EL, 0xC4192623L,
0xAD6EA6B0L, 0x49A7DF7DL, 0x9CEE60B8L, 0x8FEDB266L,
0xECAA8C71L, 0x699A17FFL, 0x5664526CL, 0xC2B19EE1L,
0x193602A5L, 0x75094C29L, 0xA0591340L, 0xE4183A3EL,
0x3F54989AL, 0x5B429D65L, 0x6B8FE4D6L, 0x99F73FD6L,
0xA1D29C07L, 0xEFE830F5L, 0x4D2D38E6L, 0xF0255DC1L,
0x4CDD2086L, 0x8470EB26L, 0x6382E9C6L, 0x021ECC5EL,
0x09686B3FL, 0x3EBAEFC9L, 0x3C971814L, 0x6B6A70A1L,
0x687F3584L, 0x52A0E286L, 0xB79C5305L, 0xAA500737L,
0x3E07841CL, 0x7FDEAE5CL, 0x8E7D44ECL, 0x5716F2B8L,
0xB03ADA37L, 0xF0500C0DL, 0xF01C1F04L, 0x0200B3FFL,
0xAE0CF51AL, 0x3CB574B2L, 0x25837A58L, 0xDC0921BDL,
0xD19113F9L, 0x7CA92FF6L, 0x94324773L, 0x22F54701L,
0x3AE5E581L, 0x37C2DADCL, 0xC8B57634L, 0x9AF3DDA7L,
0xA9446146L, 0x0FD0030EL, 0xECC8C73EL, 0xA4751E41L,
0xE238CD99L, 0x3BEA0E2FL, 0x3280BBA1L, 0x183EB331L,
0x4E548B38L, 0x4F6DB908L, 0x6F420D03L, 0xF60A04BFL,
0x2CB81290L, 0x24977C79L, 0x5679B072L, 0xBCAF89AFL,
0xDE9A771FL, 0xD9930810L, 0xB38BAE12L, 0xDCCF3F2EL,
0x5512721FL, 0x2E6B7124L, 0x501ADDE6L, 0x9F84CD87L,
0x7A584718L, 0x7408DA17L, 0xBC9F9ABCL, 0xE94B7D8CL,
0xEC7AEC3AL, 0xDB851DFAL, 0x63094366L, 0xC464C3D2L,
0xEF1C1847L, 0x3215D908L, 0xDD433B37L, 0x24C2BA16L,
0x12A14D43L, 0x2A65C451L, 0x50940002L, 0x133AE4DDL,
0x71DFF89EL, 0x10314E55L, 0x81AC77D6L, 0x5F11199BL,
0x043556F1L, 0xD7A3C76BL, 0x3C11183BL, 0x5924A509L,
0xF28FE6EDL, 0x97F1FBFAL, 0x9EBABF2CL, 0x1E153C6EL,
0x86E34570L, 0xEAE96FB1L, 0x860E5E0AL, 0x5A3E2AB3L,
0x771FE71CL, 0x4E3D06FAL, 0x2965DCB9L, 0x99E71D0FL,
0x803E89D6L, 0x5266C825L, 0x2E4CC978L, 0x9C10B36AL,
0xC6150EBAL, 0x94E2EA78L, 0xA5FC3C53L, 0x1E0A2DF4L,
0xF2F74EA7L, 0x361D2B3DL, 0x1939260FL, 0x19C27960L,
0x5223A708L, 0xF71312B6L, 0xEBADFE6EL, 0xEAC31F66L,
0xE3BC4595L, 0xA67BC883L, 0xB17F37D1L, 0x018CFF28L,
0xC332DDEFL, 0xBE6C5AA5L, 0x65582185L, 0x68AB9802L,
0xEECEA50FL, 0xDB2F953BL, 0x2AEF7DADL, 0x5B6E2F84L,
0x1521B628L, 0x29076170L, 0xECDD4775L, 0x619F1510L,
0x13CCA830L, 0xEB61BD96L, 0x0334FE1EL, 0xAA0363CFL,
0xB5735C90L, 0x4C70A239L, 0xD59E9E0BL, 0xCBAADE14L,
0xEECC86BCL, 0x60622CA7L, 0x9CAB5CABL, 0xB2F3846EL,
0x648B1EAFL, 0x19BDF0CAL, 0xA02369B9L, 0x655ABB50L,
0x40685A32L, 0x3C2AB4B3L, 0x319EE9D5L, 0xC021B8F7L,
0x9B540B19L, 0x875FA099L, 0x95F7997EL, 0x623D7DA8L,
0xF837889AL, 0x97E32D77L, 0x11ED935FL, 0x16681281L,
0x0E358829L, 0xC7E61FD6L, 0x96DEDFA1L, 0x7858BA99L,
0x57F584A5L, 0x1B227263L, 0x9B83C3FFL, 0x1AC24696L,
0xCDB30AEBL, 0x532E3054L, 0x8FD948E4L, 0x6DBC3128L,
0x58EBF2EFL, 0x34C6FFEAL, 0xFE28ED61L, 0xEE7C3C73L,
0x5D4A14D9L, 0xE864B7E3L, 0x42105D14L, 0x203E13E0L,
0x45EEE2B6L, 0xA3AAABEAL, 0xDB6C4F15L, 0xFACB4FD0L,
0xC742F442L, 0xEF6ABBB5L, 0x654F3B1DL, 0x41CD2105L,
0xD81E799EL, 0x86854DC7L, 0xE44B476AL, 0x3D816250L,
0xCF62A1F2L, 0x5B8D2646L, 0xFC8883A0L, 0xC1C7B6A3L,
0x7F1524C3L, 0x69CB7492L, 0x47848A0BL, 0x5692B285L,
0x095BBF00L, 0xAD19489DL, 0x1462B174L, 0x23820E00L,
0x58428D2AL, 0x0C55F5EAL, 0x1DADF43EL, 0x233F7061L,
0x3372F092L, 0x8D937E41L, 0xD65FECF1L, 0x6C223BDBL,
0x7CDE3759L, 0xCBEE7460L, 0x4085F2A7L, 0xCE77326EL,
0xA6078084L, 0x19F8509EL, 0xE8EFD855L, 0x61D99735L,
0xA969A7AAL, 0xC50C06C2L, 0x5A04ABFCL, 0x800BCADCL,
0x9E447A2EL, 0xC3453484L, 0xFDD56705L, 0x0E1E9EC9L,
0xDB73DBD3L, 0x105588CDL, 0x675FDA79L, 0xE3674340L,
0xC5C43465L, 0x713E38D8L, 0x3D28F89EL, 0xF16DFF20L,
0x153E21E7L, 0x8FB03D4AL, 0xE6E39F2BL, 0xDB83ADF7L },
{ 0xE93D5A68L, 0x948140F7L, 0xF64C261CL, 0x94692934L,
0x411520F7L, 0x7602D4F7L, 0xBCF46B2EL, 0xD4A20068L,
0xD4082471L, 0x3320F46AL, 0x43B7D4B7L, 0x500061AFL,
0x1E39F62EL, 0x97244546L, 0x14214F74L, 0xBF8B8840L,
0x4D95FC1DL, 0x96B591AFL, 0x70F4DDD3L, 0x66A02F45L,
0xBFBC09ECL, 0x03BD9785L, 0x7FAC6DD0L, 0x31CB8504L,
0x96EB27B3L, 0x55FD3941L, 0xDA2547E6L, 0xABCA0A9AL,
0x28507825L, 0x530429F4L, 0x0A2C86DAL, 0xE9B66DFBL,
0x68DC1462L, 0xD7486900L, 0x680EC0A4L, 0x27A18DEEL,
0x4F3FFEA2L, 0xE887AD8CL, 0xB58CE006L, 0x7AF4D6B6L,
0xAACE1E7CL, 0xD3375FECL, 0xCE78A399L, 0x406B2A42L,
0x20FE9E35L, 0xD9F385B9L, 0xEE39D7ABL, 0x3B124E8BL,
0x1DC9FAF7L, 0x4B6D1856L, 0x26A36631L, 0xEAE397B2L,
0x3A6EFA74L, 0xDD5B4332L, 0x6841E7F7L, 0xCA7820FBL,
0xFB0AF54EL, 0xD8FEB397L, 0x454056ACL, 0xBA489527L,
0x55533A3AL, 0x20838D87L, 0xFE6BA9B7L, 0xD096954BL,
0x55A867BCL, 0xA1159A58L, 0xCCA92963L, 0x99E1DB33L,
0xA62A4A56L, 0x3F3125F9L, 0x5EF47E1CL, 0x9029317CL,
0xFDF8E802L, 0x04272F70L, 0x80BB155CL, 0x05282CE3L,
0x95C11548L, 0xE4C66D22L, 0x48C1133FL, 0xC70F86DCL,
0x07F9C9EEL, 0x41041F0FL, 0x404779A4L, 0x5D886E17L,
0x325F51EBL, 0xD59BC0D1L, 0xF2BCC18FL, 0x41113564L,
0x257B7834L, 0x602A9C60L, 0xDFF8E8A3L, 0x1F636C1BL,
0x0E12B4C2L, 0x02E1329EL, 0xAF664FD1L, 0xCAD18115L,
0x6B2395E0L, 0x333E92E1L, 0x3B240B62L, 0xEEBEB922L,
0x85B2A20EL, 0xE6BA0D99L, 0xDE720C8CL, 0x2DA2F728L,
0xD0127845L, 0x95B794FDL, 0x647D0862L, 0xE7CCF5F0L,
0x5449A36FL, 0x877D48FAL, 0xC39DFD27L, 0xF33E8D1EL,
0x0A476341L, 0x992EFF74L, 0x3A6F6EABL, 0xF4F8FD37L,
0xA812DC60L, 0xA1EBDDF8L, 0x991BE14CL, 0xDB6E6B0DL,
0xC67B5510L, 0x6D672C37L, 0x2765D43BL, 0xDCD0E804L,
0xF1290DC7L, 0xCC00FFA3L, 0xB5390F92L, 0x690FED0BL,
0x667B9FFBL, 0xCEDB7D9CL, 0xA091CF0BL, 0xD9155EA3L,
0xBB132F88L, 0x515BAD24L, 0x7B9479BFL, 0x763BD6EBL,
0x37392EB3L, 0xCC115979L, 0x8026E297L, 0xF42E312DL,
0x6842ADA7L, 0xC66A2B3BL, 0x12754CCCL, 0x782EF11CL,
0x6A124237L, 0xB79251E7L, 0x06A1BBE6L, 0x4BFB6350L,
0x1A6B1018L, 0x11CAEDFAL, 0x3D25BDD8L, 0xE2E1C3C9L,
0x44421659L, 0x0A121386L, 0xD90CEC6EL, 0xD5ABEA2AL,
0x64AF674EL, 0xDA86A85FL, 0xBEBFE988L, 0x64E4C3FEL,
0x9DBC8057L, 0xF0F7C086L, 0x60787BF8L, 0x6003604DL,
0xD1FD8346L, 0xF6381FB0L, 0x7745AE04L, 0xD736FCCCL,
0x83426B33L, 0xF01EAB71L, 0xB0804187L, 0x3C005E5FL,
0x77A057BEL, 0xBDE8AE24L, 0x55464299L, 0xBF582E61L,
0x4E58F48FL, 0xF2DDFDA2L, 0xF474EF38L, 0x8789BDC2L,
0x5366F9C3L, 0xC8B38E74L, 0xB475F255L, 0x46FCD9B9L,
0x7AEB2661L, 0x8B1DDF84L, 0x846A0E79L, 0x915F95E2L,
0x466E598EL, 0x20B45770L, 0x8CD55591L, 0xC902DE4CL,
0xB90BACE1L, 0xBB8205D0L, 0x11A86248L, 0x7574A99EL,
0xB77F19B6L, 0xE0A9DC09L, 0x662D09A1L, 0xC4324633L,
0xE85A1F02L, 0x09F0BE8CL, 0x4A99A025L, 0x1D6EFE10L,
0x1AB93D1DL, 0x0BA5A4DFL, 0xA186F20FL, 0x2868F169L,
0xDCB7DA83L, 0x573906FEL, 0xA1E2CE9BL, 0x4FCD7F52L,
0x50115E01L, 0xA70683FAL, 0xA002B5C4L, 0x0DE6D027L,
0x9AF88C27L, 0x773F8641L, 0xC3604C06L, 0x61A806B5L,
0xF0177A28L, 0xC0F586E0L, 0x006058AAL, 0x30DC7D62L,
0x11E69ED7L, 0x2338EA63L, 0x53C2DD94L, 0xC2C21634L,
0xBBCBEE56L, 0x90BCB6DEL, 0xEBFC7DA1L, 0xCE591D76L,
0x6F05E409L, 0x4B7C0188L, 0x39720A3DL, 0x7C927C24L,
0x86E3725FL, 0x724D9DB9L, 0x1AC15BB4L, 0xD39EB8FCL,
0xED545578L, 0x08FCA5B5L, 0xD83D7CD3L, 0x4DAD0FC4L,
0x1E50EF5EL, 0xB161E6F8L, 0xA28514D9L, 0x6C51133CL,
0x6FD5C7E7L, 0x56E14EC4L, 0x362ABFCEL, 0xDDC6C837L,
0xD79A3234L, 0x92638212L, 0x670EFA8EL, 0x406000E0L },
{ 0x3A39CE37L, 0xD3FAF5CFL, 0xABC27737L, 0x5AC52D1BL,
0x5CB0679EL, 0x4FA33742L, 0xD3822740L, 0x99BC9BBEL,
0xD5118E9DL, 0xBF0F7315L, 0xD62D1C7EL, 0xC700C47BL,
0xB78C1B6BL, 0x21A19045L, 0xB26EB1BEL, 0x6A366EB4L,
0x5748AB2FL, 0xBC946E79L, 0xC6A376D2L, 0x6549C2C8L,
0x530FF8EEL, 0x468DDE7DL, 0xD5730A1DL, 0x4CD04DC6L,
0x2939BBDBL, 0xA9BA4650L, 0xAC9526E8L, 0xBE5EE304L,
0xA1FAD5F0L, 0x6A2D519AL, 0x63EF8CE2L, 0x9A86EE22L,
0xC089C2B8L, 0x43242EF6L, 0xA51E03AAL, 0x9CF2D0A4L,
0x83C061BAL, 0x9BE96A4DL, 0x8FE51550L, 0xBA645BD6L,
0x2826A2F9L, 0xA73A3AE1L, 0x4BA99586L, 0xEF5562E9L,
0xC72FEFD3L, 0xF752F7DAL, 0x3F046F69L, 0x77FA0A59L,
0x80E4A915L, 0x87B08601L, 0x9B09E6ADL, 0x3B3EE593L,
0xE990FD5AL, 0x9E34D797L, 0x2CF0B7D9L, 0x022B8B51L,
0x96D5AC3AL, 0x017DA67DL, 0xD1CF3ED6L, 0x7C7D2D28L,
0x1F9F25CFL, 0xADF2B89BL, 0x5AD6B472L, 0x5A88F54CL,
0xE029AC71L, 0xE019A5E6L, 0x47B0ACFDL, 0xED93FA9BL,
0xE8D3C48DL, 0x283B57CCL, 0xF8D56629L, 0x79132E28L,
0x785F0191L, 0xED756055L, 0xF7960E44L, 0xE3D35E8CL,
0x15056DD4L, 0x88F46DBAL, 0x03A16125L, 0x0564F0BDL,
0xC3EB9E15L, 0x3C9057A2L, 0x97271AECL, 0xA93A072AL,
0x1B3F6D9BL, 0x1E6321F5L, 0xF59C66FBL, 0x26DCF319L,
0x7533D928L, 0xB155FDF5L, 0x03563482L, 0x8ABA3CBBL,
0x28517711L, 0xC20AD9F8L, 0xABCC5167L, 0xCCAD925FL,
0x4DE81751L, 0x3830DC8EL, 0x379D5862L, 0x9320F991L,
0xEA7A90C2L, 0xFB3E7BCEL, 0x5121CE64L, 0x774FBE32L,
0xA8B6E37EL, 0xC3293D46L, 0x48DE5369L, 0x6413E680L,
0xA2AE0810L, 0xDD6DB224L, 0x69852DFDL, 0x09072166L,
0xB39A460AL, 0x6445C0DDL, 0x586CDECFL, 0x1C20C8AEL,
0x5BBEF7DDL, 0x1B588D40L, 0xCCD2017FL, 0x6BB4E3BBL,
0xDDA26A7EL, 0x3A59FF45L, 0x3E350A44L, 0xBCB4CDD5L,
0x72EACEA8L, 0xFA6484BBL, 0x8D6612AEL, 0xBF3C6F47L,
0xD29BE463L, 0x542F5D9EL, 0xAEC2771BL, 0xF64E6370L,
0x740E0D8DL, 0xE75B1357L, 0xF8721671L, 0xAF537D5DL,
0x4040CB08L, 0x4EB4E2CCL, 0x34D2466AL, 0x0115AF84L,
0xE1B00428L, 0x95983A1DL, 0x06B89FB4L, 0xCE6EA048L,
0x6F3F3B82L, 0x3520AB82L, 0x011A1D4BL, 0x277227F8L,
0x611560B1L, 0xE7933FDCL, 0xBB3A792BL, 0x344525BDL,
0xA08839E1L, 0x51CE794BL, 0x2F32C9B7L, 0xA01FBAC9L,
0xE01CC87EL, 0xBCC7D1F6L, 0xCF0111C3L, 0xA1E8AAC7L,
0x1A908749L, 0xD44FBD9AL, 0xD0DADECBL, 0xD50ADA38L,
0x0339C32AL, 0xC6913667L, 0x8DF9317CL, 0xE0B12B4FL,
0xF79E59B7L, 0x43F5BB3AL, 0xF2D519FFL, 0x27D9459CL,
0xBF97222CL, 0x15E6FC2AL, 0x0F91FC71L, 0x9B941525L,
0xFAE59361L, 0xCEB69CEBL, 0xC2A86459L, 0x12BAA8D1L,
0xB6C1075EL, 0xE3056A0CL, 0x10D25065L, 0xCB03A442L,
0xE0EC6E0EL, 0x1698DB3BL, 0x4C98A0BEL, 0x3278E964L,
0x9F1F9532L, 0xE0D392DFL, 0xD3A0342BL, 0x8971F21EL,
0x1B0A7441L, 0x4BA3348CL, 0xC5BE7120L, 0xC37632D8L,
0xDF359F8DL, 0x9B992F2EL, 0xE60B6F47L, 0x0FE3F11DL,
0xE54CDA54L, 0x1EDAD891L, 0xCE6279CFL, 0xCD3E7E6FL,
0x1618B166L, 0xFD2C1D05L, 0x848FD2C5L, 0xF6FB2299L,
0xF523F357L, 0xA6327623L, 0x93A83531L, 0x56CCCD02L,
0xACF08162L, 0x5A75EBB5L, 0x6E163697L, 0x88D273CCL,
0xDE966292L, 0x81B949D0L, 0x4C50901BL, 0x71C65614L,
0xE6C6C7BDL, 0x327A140AL, 0x45E1D006L, 0xC3F27B9AL,
0xC9AA53FDL, 0x62A80F00L, 0xBB25BFE2L, 0x35BDD2F6L,
0x71126905L, 0xB2040222L, 0xB6CBCF7CL, 0xCD769C2BL,
0x53113EC0L, 0x1640E3D3L, 0x38ABBD60L, 0x2547ADF0L,
0xBA38209CL, 0xF746CE76L, 0x77AFA1C5L, 0x20756060L,
0x85CBFE4EL, 0x8AE88DD8L, 0x7AAAF9B0L, 0x4CF9AA7EL,
0x1948C25CL, 0x02FB8A8CL, 0x01C36AE4L, 0xD6EBE1F9L,
0x90D4F869L, 0xA65CDEA0L, 0x3F09252DL, 0xC208E69FL,
0xB74E6132L, 0xCE77E25BL, 0x578FDFE3L, 0x3AC372E6L }
};
#endif /* !POLARSSL_BLOWFISH_ALT */
#endif /* POLARSSL_BLOWFISH_C */
File diff suppressed because it is too large Load Diff
-196
View File
@@ -1,196 +0,0 @@
/*
* X.509 test certificates
*
* Copyright (C) 2006-2010, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_CERTS_C)
const char test_ca_crt[] =
"-----BEGIN CERTIFICATE-----\r\n"
"MIIDhzCCAm+gAwIBAgIBADANBgkqhkiG9w0BAQUFADA7MQswCQYDVQQGEwJOTDER\r\n"
"MA8GA1UEChMIUG9sYXJTU0wxGTAXBgNVBAMTEFBvbGFyU1NMIFRlc3QgQ0EwHhcN\r\n"
"MTEwMjEyMTQ0NDAwWhcNMjEwMjEyMTQ0NDAwWjA7MQswCQYDVQQGEwJOTDERMA8G\r\n"
"A1UEChMIUG9sYXJTU0wxGTAXBgNVBAMTEFBvbGFyU1NMIFRlc3QgQ0EwggEiMA0G\r\n"
"CSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDA3zf8F7vglp0/ht6WMn1EpRagzSHx\r\n"
"mdTs6st8GFgIlKXsm8WL3xoemTiZhx57wI053zhdcHgH057Zk+i5clHFzqMwUqny\r\n"
"50BwFMtEonILwuVA+T7lpg6z+exKY8C4KQB0nFc7qKUEkHHxvYPZP9al4jwqj+8n\r\n"
"YMPGn8u67GB9t+aEMr5P+1gmIgNb1LTV+/Xjli5wwOQuvfwu7uJBVcA0Ln0kcmnL\r\n"
"R7EUQIN9Z/SG9jGr8XmksrUuEvmEF/Bibyc+E1ixVA0hmnM3oTDPb5Lc9un8rNsu\r\n"
"KNF+AksjoBXyOGVkCeoMbo4bF6BxyLObyavpw/LPh5aPgAIynplYb6LVAgMBAAGj\r\n"
"gZUwgZIwDAYDVR0TBAUwAwEB/zAdBgNVHQ4EFgQUtFrkpbPe0lL2udWmlQ/rPrzH\r\n"
"/f8wYwYDVR0jBFwwWoAUtFrkpbPe0lL2udWmlQ/rPrzH/f+hP6Q9MDsxCzAJBgNV\r\n"
"BAYTAk5MMREwDwYDVQQKEwhQb2xhclNTTDEZMBcGA1UEAxMQUG9sYXJTU0wgVGVz\r\n"
"dCBDQYIBADANBgkqhkiG9w0BAQUFAAOCAQEAuP1U2ABUkIslsCfdlc2i94QHHYeJ\r\n"
"SsR4EdgHtdciUI5I62J6Mom+Y0dT/7a+8S6MVMCZP6C5NyNyXw1GWY/YR82XTJ8H\r\n"
"DBJiCTok5DbZ6SzaONBzdWHXwWwmi5vg1dxn7YxrM9d0IjxM27WNKs4sDQhZBQkF\r\n"
"pjmfs2cb4oPl4Y9T9meTx/lvdkRYEug61Jfn6cA+qHpyPYdTH+UshITnmp5/Ztkf\r\n"
"m/UTSLBNFNHesiTZeH31NcxYGdHSme9Nc/gfidRa0FLOCfWxRlFqAI47zG9jAQCZ\r\n"
"7Z2mCGDNMhjQc+BYcdnl0lPXjdDK6V0qCg1dVewhUBcW5gZKzV7e9+DpVA==\r\n"
"-----END CERTIFICATE-----\r\n";
const char test_ca_key[] =
"-----BEGIN RSA PRIVATE KEY-----\r\n"
"Proc-Type: 4,ENCRYPTED\r\n"
"DEK-Info: DES-EDE3-CBC,A8A95B05D5B7206B\r\n"
"\r\n"
"9Qd9GeArejl1GDVh2lLV1bHt0cPtfbh5h/5zVpAVaFpqtSPMrElp50Rntn9et+JA\r\n"
"7VOyboR+Iy2t/HU4WvA687k3Bppe9GwKHjHhtl//8xFKwZr3Xb5yO5JUP8AUctQq\r\n"
"Nb8CLlZyuUC+52REAAthdWgsX+7dJO4yabzUcQ22Tp9JSD0hiL43BlkWYUNK3dAo\r\n"
"PZlmiptjnzVTjg1MxsBSydZinWOLBV8/JQgxSPo2yD4uEfig28qbvQ2wNIn0pnAb\r\n"
"GxnSAOazkongEGfvcjIIs+LZN9gXFhxcOh6kc4Q/c99B7QWETwLLkYgZ+z1a9VY9\r\n"
"gEU7CwCxYCD+h9hY6FPmsK0/lC4O7aeRKpYq00rPPxs6i7phiexg6ax6yTMmArQq\r\n"
"QmK3TAsJm8V/J5AWpLEV6jAFgRGymGGHnof0DXzVWZidrcZJWTNuGEX90nB3ee2w\r\n"
"PXJEFWKoD3K3aFcSLdHYr3mLGxP7H9ThQai9VsycxZKS5kwvBKQ//YMrmFfwPk8x\r\n"
"vTeY4KZMaUrveEel5tWZC94RSMKgxR6cyE1nBXyTQnDOGbfpNNgBKxyKbINWoOJU\r\n"
"WJZAwlsQn+QzCDwpri7+sV1mS3gBE6UY7aQmnmiiaC2V3Hbphxct/en5QsfDOt1X\r\n"
"JczSfpRWLlbPznZg8OQh/VgCMA58N5DjOzTIK7sJJ5r+94ZBTCpgAMbF588f0NTR\r\n"
"KCe4yrxGJR7X02M4nvD4IwOlpsQ8xQxZtOSgXv4LkxvdU9XJJKWZ/XNKJeWztxSe\r\n"
"Z1vdTc2YfsDBA2SEv33vxHx2g1vqtw8SjDRT2RaQSS0QuSaMJimdOX6mTOCBKk1J\r\n"
"9Q5mXTrER+/LnK0jEmXsBXWA5bqqVZIyahXSx4VYZ7l7w/PHiUDtDgyRhMMKi4n2\r\n"
"iQvQcWSQTjrpnlJbca1/DkpRt3YwrvJwdqb8asZU2VrNETh5x0QVefDRLFiVpif/\r\n"
"tUaeAe/P1F8OkS7OIZDs1SUbv/sD2vMbhNkUoCms3/PvNtdnvgL4F0zhaDpKCmlT\r\n"
"P8vx49E7v5CyRNmED9zZg4o3wmMqrQO93PtTug3Eu9oVx1zPQM1NVMyBa2+f29DL\r\n"
"1nuTCeXdo9+ni45xx+jAI4DCwrRdhJ9uzZyC6962H37H6D+5naNvClFR1s6li1Gb\r\n"
"nqPoiy/OBsEx9CaDGcqQBp5Wme/3XW+6z1ISOx+igwNTVCT14mHdBMbya0eIKft5\r\n"
"X+GnwtgEMyCYyyWuUct8g4RzErcY9+yW9Om5Hzpx4zOuW4NPZgPDTgK+t2RSL/Yq\r\n"
"rE1njrgeGYcVeG3f+OftH4s6fPbq7t1A5ZgUscbLMBqr9tK+OqygR4EgKBPsH6Cz\r\n"
"L6zlv/2RV0qAHvVuDJcIDIgwY5rJtINEm32rhOeFNJwZS5MNIC1czXZx5//ugX7l\r\n"
"I4sy5nbVhwSjtAk8Xg5dZbdTZ6mIrb7xqH+fdakZor1khG7bC2uIwibD3cSl2XkR\r\n"
"wN48lslbHnqqagr6Xm1nNOSVl8C/6kbJEsMpLhAezfRtGwvOucoaE+WbeUNolGde\r\n"
"P/eQiddSf0brnpiLJRh7qZrl9XuqYdpUqnoEdMAfotDOID8OtV7gt8a48ad8VPW2\r\n"
"-----END RSA PRIVATE KEY-----\r\n";
const char test_ca_pwd[] = "PolarSSLTest";
const char test_srv_crt[] =
"-----BEGIN CERTIFICATE-----\r\n"
"MIIDPzCCAiegAwIBAgIBATANBgkqhkiG9w0BAQUFADA7MQswCQYDVQQGEwJOTDER\r\n"
"MA8GA1UEChMIUG9sYXJTU0wxGTAXBgNVBAMTEFBvbGFyU1NMIFRlc3QgQ0EwHhcN\r\n"
"MTEwMjEyMTQ0NDA2WhcNMjEwMjEyMTQ0NDA2WjA8MQswCQYDVQQGEwJOTDERMA8G\r\n"
"A1UEChMIUG9sYXJTU0wxGjAYBgNVBAMTEVBvbGFyU1NMIFNlcnZlciAxMIIBIjAN\r\n"
"BgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAqQIfPUBq1VVTi/027oJlLhVhXom/\r\n"
"uOhFkNvuiBZS0/FDUEeWEllkh2v9K+BG+XO+3c+S4ZFb7Wagb4kpeUWA0INq1UFD\r\n"
"d185fAkER4KwVzlw7aPsFRkeqDMIR8EFQqn9TMO0390GH00QUUBncxMPQPhtgSVf\r\n"
"CrFTxjB+FTms+Vruf5KepgVb5xOXhbUjktnUJAbVCSWJdQfdphqPPwkZvq1lLGTr\r\n"
"lZvc/kFeF6babFtpzAK6FCwWJJxK3M3Q91Jnc/EtoCP9fvQxyi1wyokLBNsupk9w\r\n"
"bp7OvViJ4lNZnm5akmXiiD8MlBmj3eXonZUT7Snbq3AS3FrKaxerUoJUsQIDAQAB\r\n"
"o00wSzAJBgNVHRMEAjAAMB0GA1UdDgQWBBQfdNY/KcF0dEU7BRIsPai9Q1kCpjAf\r\n"
"BgNVHSMEGDAWgBS0WuSls97SUva51aaVD+s+vMf9/zANBgkqhkiG9w0BAQUFAAOC\r\n"
"AQEAvc+WwZUemsJu2IiI2Cp6liA+UAvIx98dQe3kZs2zAoF9VwQbXcYzWQ/BILkj\r\n"
"NImKbPL9x0g2jIDn4ZvGYFywMwIO/d++YbwYiQw42/v7RiMy94zBPnzeHi86dy/0\r\n"
"jpOOJUx3IXRsGLdyjb/1T11klcFqGnARiK+8VYolMPP6afKvLXX7K4kiUpsFQhUp\r\n"
"E5VeM5pV1Mci2ETOJau2cO40FJvI/C9W/wR+GAArMaw2fxG77E3laaa0LAOlexM6\r\n"
"A4KOb5f5cGTM5Ih6tEF5FVq3/9vzNIYMa1FqzacBLZF8zSHYLEimXBdzjBoN4qDU\r\n"
"/WzRyYRBRjAI49mzHX6raleqnw==\r\n"
"-----END CERTIFICATE-----\r\n";
const char test_srv_key[] =
"-----BEGIN RSA PRIVATE KEY-----\r\n"
"MIIEogIBAAKCAQEAqQIfPUBq1VVTi/027oJlLhVhXom/uOhFkNvuiBZS0/FDUEeW\r\n"
"Ellkh2v9K+BG+XO+3c+S4ZFb7Wagb4kpeUWA0INq1UFDd185fAkER4KwVzlw7aPs\r\n"
"FRkeqDMIR8EFQqn9TMO0390GH00QUUBncxMPQPhtgSVfCrFTxjB+FTms+Vruf5Ke\r\n"
"pgVb5xOXhbUjktnUJAbVCSWJdQfdphqPPwkZvq1lLGTrlZvc/kFeF6babFtpzAK6\r\n"
"FCwWJJxK3M3Q91Jnc/EtoCP9fvQxyi1wyokLBNsupk9wbp7OvViJ4lNZnm5akmXi\r\n"
"iD8MlBmj3eXonZUT7Snbq3AS3FrKaxerUoJUsQIDAQABAoIBABaJ9eiRQq4Ypv+w\r\n"
"UTcVpLC0oTueWzcpor1i1zjG4Vzqe/Ok2FqyGToGKMlFK7Hwwa+LEyeJ3xyV5yd4\r\n"
"v1Mw9bDZFdJC1eCBjoUAHtX6k9HOE0Vd6woVQ4Vi6OPI1g7B5Mnr/58rNrnN6TMs\r\n"
"x58NF6euecwTU811QJrZtLbX7j2Cr28yB2Vs8qyYlHwVw5jbDOv43D7vU5gmlIDN\r\n"
"0JQRuWAnOuPzZNoJr4SfJKqHNGxYYY6pHZ1s0dOTLIDb/B8KQWapA2kRmZyid2EH\r\n"
"nwzgLbAsHJCf+bQnhXjXuxtUsrcIL8noZLazlOMxwNEammglVWW23Ud/QRnFgJg5\r\n"
"UgcAcRECgYEA19uYetht5qmwdJ+12oC6zeO+vXLcyD9gon23T5J6w2YThld7/OW0\r\n"
"oArQJGgkAdaq0pcTyOIjtTQVMFygdVmCEJmxh/3RutPcTeydqW9fphKDMej32J8e\r\n"
"GniGmNGiclbcfNOS8E5TGp445yZb9P1+7AHng16bGg3Ykj5EA4G+HCcCgYEAyHAl\r\n"
"//ekk8YjQElm+8izLtFkymIK0aCtEe9C/RIRhFYBeFaotC5dStNhBOncn4ovMAPD\r\n"
"lX/92yDi9OP8PPLN3a4B9XpW3k/SS5GrbT5cwOivBHNllZSmu/2qz5WPGcjVCOrB\r\n"
"LYl3YWr2h3EGKICT03kEoTkiDBvCeOpW7cCGl2cCgYBD5whoXHz1+ptPlI4YVjZt\r\n"
"Xh86aU+ajpVPiEyJ84I6xXmO4SZXv8q6LaycR0ZMbcL+zBelMb4Z2nBv7jNrtuR7\r\n"
"ZF28cdPv+YVr3esaybZE/73VjXup4SQPH6r3l7qKTVi+y6+FeJ4b2Xn8/MwgnT23\r\n"
"8EFrye7wmzpthrjOgZnUMQKBgE9Lhsz/5J0Nis6Y+2Pqn3CLKEukg9Ewtqdct2y0\r\n"
"5Dcta0F3TyCRIxlCDKTL/BslqMtfAdY4H268UO0+8IAQMn9boqzBrHIgs/pvc5kx\r\n"
"TbKHmw2wtWR6vYersBKVgVpbCGSRssDYHGFu1n74qM4HJ/RGcR1zI9QUe1gopSFD\r\n"
"xDtLAoGAVAdWvrqDwgoL2hHW3scGpxdE/ygJDOwHnf+1B9goKAOP5lf2FJaiAxf3\r\n"
"ectoPOgZbCmm/iiDmigu703ld3O+VoCLDD4qx3R+KyALL78gtVJYzSRiKhzgCZ3g\r\n"
"mKsIVRBq4IfwiwyMNG2BYZQAwbSDjjPtn/kPBduPzPj7eriByhI=\r\n"
"-----END RSA PRIVATE KEY-----\r\n";
const char test_cli_crt[] =
"-----BEGIN CERTIFICATE-----\r\n"
"MIIDPzCCAiegAwIBAgIBBDANBgkqhkiG9w0BAQUFADA7MQswCQYDVQQGEwJOTDER\r\n"
"MA8GA1UEChMIUG9sYXJTU0wxGTAXBgNVBAMTEFBvbGFyU1NMIFRlc3QgQ0EwHhcN\r\n"
"MTEwMjEyMTQ0NDA3WhcNMjEwMjEyMTQ0NDA3WjA8MQswCQYDVQQGEwJOTDERMA8G\r\n"
"A1UEChMIUG9sYXJTU0wxGjAYBgNVBAMTEVBvbGFyU1NMIENsaWVudCAyMIIBIjAN\r\n"
"BgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAyHTEzLn5tXnpRdkUYLB9u5Pyax6f\r\n"
"M60Nj4o8VmXl3ETZzGaFB9X4J7BKNdBjngpuG7fa8H6r7gwQk4ZJGDTzqCrSV/Uu\r\n"
"1C93KYRhTYJQj6eVSHD1bk2y1RPD0hrt5kPqQhTrdOrA7R/UV06p86jt0uDBMHEw\r\n"
"MjDV0/YI0FZPRo7yX/k9Z5GIMC5Cst99++UMd//sMcB4j7/Cf8qtbCHWjdmLao5v\r\n"
"4Jv4EFbMs44TFeY0BGbH7vk2DmqV9gmaBmf0ZXH4yqSxJeD+PIs1BGe64E92hfx/\r\n"
"/DZrtenNLQNiTrM9AM+vdqBpVoNq0qjU51Bx5rU2BXcFbXvI5MT9TNUhXwIDAQAB\r\n"
"o00wSzAJBgNVHRMEAjAAMB0GA1UdDgQWBBRxoQBzckAvVHZeM/xSj7zx3WtGITAf\r\n"
"BgNVHSMEGDAWgBS0WuSls97SUva51aaVD+s+vMf9/zANBgkqhkiG9w0BAQUFAAOC\r\n"
"AQEAAn86isAM8X+mVwJqeItt6E9slhEQbAofyk+diH1Lh8Y9iLlWQSKbw/UXYjx5\r\n"
"LLPZcniovxIcARC/BjyZR9g3UwTHNGNm+rwrqa15viuNOFBchykX/Orsk02EH7NR\r\n"
"Alw5WLPorYjED6cdVQgBl9ot93HdJogRiXCxErM7NC8/eP511mjq+uLDjLKH8ZPQ\r\n"
"8I4ekHJnroLsDkIwXKGIsvIBHQy2ac/NwHLCQOK6mfum1pRx52V4Utu5dLLjD5bM\r\n"
"xOBC7KU4xZKuMXXZM6/93Yb51K/J4ahf1TxJlTWXtnzDr9saEYdNy2SKY/6ZiDNH\r\n"
"D+stpAKiQLAWaAusIWKYEyw9MQ==\r\n"
"-----END CERTIFICATE-----\r\n";
const char test_cli_key[] =
"-----BEGIN RSA PRIVATE KEY-----\r\n"
"MIIEpAIBAAKCAQEAyHTEzLn5tXnpRdkUYLB9u5Pyax6fM60Nj4o8VmXl3ETZzGaF\r\n"
"B9X4J7BKNdBjngpuG7fa8H6r7gwQk4ZJGDTzqCrSV/Uu1C93KYRhTYJQj6eVSHD1\r\n"
"bk2y1RPD0hrt5kPqQhTrdOrA7R/UV06p86jt0uDBMHEwMjDV0/YI0FZPRo7yX/k9\r\n"
"Z5GIMC5Cst99++UMd//sMcB4j7/Cf8qtbCHWjdmLao5v4Jv4EFbMs44TFeY0BGbH\r\n"
"7vk2DmqV9gmaBmf0ZXH4yqSxJeD+PIs1BGe64E92hfx//DZrtenNLQNiTrM9AM+v\r\n"
"dqBpVoNq0qjU51Bx5rU2BXcFbXvI5MT9TNUhXwIDAQABAoIBAGdNtfYDiap6bzst\r\n"
"yhCiI8m9TtrhZw4MisaEaN/ll3XSjaOG2dvV6xMZCMV+5TeXDHOAZnY18Yi18vzz\r\n"
"4Ut2TnNFzizCECYNaA2fST3WgInnxUkV3YXAyP6CNxJaCmv2aA0yFr2kFVSeaKGt\r\n"
"ymvljNp2NVkvm7Th8fBQBO7I7AXhz43k0mR7XmPgewe8ApZOG3hstkOaMvbWAvWA\r\n"
"zCZupdDjZYjOJqlA4eEA4H8/w7F83r5CugeBE8LgEREjLPiyejrU5H1fubEY+h0d\r\n"
"l5HZBJ68ybTXfQ5U9o/QKA3dd0toBEhhdRUDGzWtjvwkEQfqF1reGWj/tod/gCpf\r\n"
"DFi6X0ECgYEA4wOv/pjSC3ty6TuOvKX2rOUiBrLXXv2JSxZnMoMiWI5ipLQt+RYT\r\n"
"VPafL/m7Dn6MbwjayOkcZhBwk5CNz5A6Q4lJ64Mq/lqHznRCQQ2Mc1G8eyDF/fYL\r\n"
"Ze2pLvwP9VD5jTc2miDfw+MnvJhywRRLcemDFP8k4hQVtm8PMp3ZmNECgYEA4gz7\r\n"
"wzObR4gn8ibe617uQPZjWzUj9dUHYd+in1gwBCIrtNnaRn9I9U/Q6tegRYpii4ys\r\n"
"c176NmU+umy6XmuSKV5qD9bSpZWG2nLFnslrN15Lm3fhZxoeMNhBaEDTnLT26yoi\r\n"
"33gp0mSSWy94ZEqipms+ULF6sY1ZtFW6tpGFoy8CgYAQHhnnvJflIs2ky4q10B60\r\n"
"ZcxFp3rtDpkp0JxhFLhiizFrujMtZSjYNm5U7KkgPVHhLELEUvCmOnKTt4ap/vZ0\r\n"
"BxJNe1GZH3pW6SAvGDQpl9sG7uu/vTFP+lCxukmzxB0DrrDcvorEkKMom7ZCCRvW\r\n"
"KZsZ6YeH2Z81BauRj218kQKBgQCUV/DgKP2985xDTT79N08jUo3hTP5MVYCCuj/+\r\n"
"UeEw1TvZcx3LJby7P6Xad6a1/BqveaGyFKIfEFIaBUBItk801sDDpDaYc4gL00Xc\r\n"
"7lFuBHOZkxJYlss5QrGpuOEl9ZwUt5IrFLBdYaKqNHzNVC1pCPfb/JyH6Dr2HUxq\r\n"
"gxUwAQKBgQCcU6G2L8AG9d9c0UpOyL1tMvFe5Ttw0KjlQVdsh1MP6yigYo9DYuwu\r\n"
"bHFVW2r0dBTqegP2/KTOxKzaHfC1qf0RGDsUoJCNJrd1cwoCLG8P2EF4w3OBrKqv\r\n"
"8u4ytY0F+Vlanj5lm3TaoHSVF1+NWPyOTiwevIECGKwSxvlki4fDAA==\r\n"
"-----END RSA PRIVATE KEY-----\r\n";
const char test_dhm_params[] =
"-----BEGIN DH PARAMETERS-----\r\n"
"MIGHAoGBAJ419DBEOgmQTzo5qXl5fQcN9TN455wkOL7052HzxxRVMyhYmwQcgJvh\r\n"
"1sa18fyfR9OiVEMYglOpkqVoGLN7qd5aQNNi5W7/C+VBdHTBJcGZJyyP5B3qcz32\r\n"
"9mLJKudlVudV0Qxk5qUJaPZ/xupz0NyoVpviuiBOI1gNi8ovSXWzAgEC\r\n"
"-----END DH PARAMETERS-----\r\n";
#endif
-602
View File
@@ -1,602 +0,0 @@
/**
* \file cipher.c
*
* \brief Generic cipher wrapper for PolarSSL
*
* \author Adriaan de Jong <dejong@fox-it.com>
*
* Copyright (C) 2006-2012, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_CIPHER_C)
#include "polarssl/cipher.h"
#include "polarssl/cipher_wrap.h"
#include <stdlib.h>
#include <strings.h>
#if defined _MSC_VER && !defined strcasecmp
#define strcasecmp _stricmp
#endif
static const int supported_ciphers[] = {
#if defined(POLARSSL_AES_C)
POLARSSL_CIPHER_AES_128_CBC,
POLARSSL_CIPHER_AES_192_CBC,
POLARSSL_CIPHER_AES_256_CBC,
#if defined(POLARSSL_CIPHER_MODE_CFB)
POLARSSL_CIPHER_AES_128_CFB128,
POLARSSL_CIPHER_AES_192_CFB128,
POLARSSL_CIPHER_AES_256_CFB128,
#endif /* defined(POLARSSL_CIPHER_MODE_CFB) */
#if defined(POLARSSL_CIPHER_MODE_CTR)
POLARSSL_CIPHER_AES_128_CTR,
POLARSSL_CIPHER_AES_192_CTR,
POLARSSL_CIPHER_AES_256_CTR,
#endif /* defined(POLARSSL_CIPHER_MODE_CTR) */
#endif /* defined(POLARSSL_AES_C) */
#if defined(POLARSSL_CAMELLIA_C)
POLARSSL_CIPHER_CAMELLIA_128_CBC,
POLARSSL_CIPHER_CAMELLIA_192_CBC,
POLARSSL_CIPHER_CAMELLIA_256_CBC,
#if defined(POLARSSL_CIPHER_MODE_CFB)
POLARSSL_CIPHER_CAMELLIA_128_CFB128,
POLARSSL_CIPHER_CAMELLIA_192_CFB128,
POLARSSL_CIPHER_CAMELLIA_256_CFB128,
#endif /* defined(POLARSSL_CIPHER_MODE_CFB) */
#if defined(POLARSSL_CIPHER_MODE_CTR)
POLARSSL_CIPHER_CAMELLIA_128_CTR,
POLARSSL_CIPHER_CAMELLIA_192_CTR,
POLARSSL_CIPHER_CAMELLIA_256_CTR,
#endif /* defined(POLARSSL_CIPHER_MODE_CTR) */
#endif /* defined(POLARSSL_CAMELLIA_C) */
#if defined(POLARSSL_DES_C)
POLARSSL_CIPHER_DES_CBC,
POLARSSL_CIPHER_DES_EDE_CBC,
POLARSSL_CIPHER_DES_EDE3_CBC,
#endif /* defined(POLARSSL_DES_C) */
#if defined(POLARSSL_BLOWFISH_C)
POLARSSL_CIPHER_BLOWFISH_CBC,
#if defined(POLARSSL_CIPHER_MODE_CFB)
POLARSSL_CIPHER_BLOWFISH_CFB64,
#endif /* defined(POLARSSL_CIPHER_MODE_CFB) */
#if defined(POLARSSL_CIPHER_MODE_CTR)
POLARSSL_CIPHER_BLOWFISH_CTR,
#endif /* defined(POLARSSL_CIPHER_MODE_CTR) */
#endif /* defined(POLARSSL_BLOWFISH_C) */
#if defined(POLARSSL_CIPHER_NULL_CIPHER)
POLARSSL_CIPHER_NULL,
#endif /* defined(POLARSSL_CIPHER_NULL_CIPHER) */
0
};
const int *cipher_list( void )
{
return supported_ciphers;
}
const cipher_info_t *cipher_info_from_type( const cipher_type_t cipher_type )
{
/* Find static cipher information */
switch ( cipher_type )
{
#if defined(POLARSSL_AES_C)
case POLARSSL_CIPHER_AES_128_CBC:
return &aes_128_cbc_info;
case POLARSSL_CIPHER_AES_192_CBC:
return &aes_192_cbc_info;
case POLARSSL_CIPHER_AES_256_CBC:
return &aes_256_cbc_info;
#if defined(POLARSSL_CIPHER_MODE_CFB)
case POLARSSL_CIPHER_AES_128_CFB128:
return &aes_128_cfb128_info;
case POLARSSL_CIPHER_AES_192_CFB128:
return &aes_192_cfb128_info;
case POLARSSL_CIPHER_AES_256_CFB128:
return &aes_256_cfb128_info;
#endif /* defined(POLARSSL_CIPHER_MODE_CFB) */
#if defined(POLARSSL_CIPHER_MODE_CTR)
case POLARSSL_CIPHER_AES_128_CTR:
return &aes_128_ctr_info;
case POLARSSL_CIPHER_AES_192_CTR:
return &aes_192_ctr_info;
case POLARSSL_CIPHER_AES_256_CTR:
return &aes_256_ctr_info;
#endif /* defined(POLARSSL_CIPHER_MODE_CTR) */
#endif
#if defined(POLARSSL_CAMELLIA_C)
case POLARSSL_CIPHER_CAMELLIA_128_CBC:
return &camellia_128_cbc_info;
case POLARSSL_CIPHER_CAMELLIA_192_CBC:
return &camellia_192_cbc_info;
case POLARSSL_CIPHER_CAMELLIA_256_CBC:
return &camellia_256_cbc_info;
#if defined(POLARSSL_CIPHER_MODE_CFB)
case POLARSSL_CIPHER_CAMELLIA_128_CFB128:
return &camellia_128_cfb128_info;
case POLARSSL_CIPHER_CAMELLIA_192_CFB128:
return &camellia_192_cfb128_info;
case POLARSSL_CIPHER_CAMELLIA_256_CFB128:
return &camellia_256_cfb128_info;
#endif /* defined(POLARSSL_CIPHER_MODE_CFB) */
#if defined(POLARSSL_CIPHER_MODE_CTR)
case POLARSSL_CIPHER_CAMELLIA_128_CTR:
return &camellia_128_ctr_info;
case POLARSSL_CIPHER_CAMELLIA_192_CTR:
return &camellia_192_ctr_info;
case POLARSSL_CIPHER_CAMELLIA_256_CTR:
return &camellia_256_ctr_info;
#endif /* defined(POLARSSL_CIPHER_MODE_CTR) */
#endif
#if defined(POLARSSL_DES_C)
case POLARSSL_CIPHER_DES_CBC:
return &des_cbc_info;
case POLARSSL_CIPHER_DES_EDE_CBC:
return &des_ede_cbc_info;
case POLARSSL_CIPHER_DES_EDE3_CBC:
return &des_ede3_cbc_info;
#endif
#if defined(POLARSSL_BLOWFISH_C)
case POLARSSL_CIPHER_BLOWFISH_CBC:
return &blowfish_cbc_info;
#if defined(POLARSSL_CIPHER_MODE_CFB)
case POLARSSL_CIPHER_BLOWFISH_CFB64:
return &blowfish_cfb64_info;
#endif /* defined(POLARSSL_CIPHER_MODE_CFB) */
#if defined(POLARSSL_CIPHER_MODE_CTR)
case POLARSSL_CIPHER_BLOWFISH_CTR:
return &blowfish_ctr_info;
#endif /* defined(POLARSSL_CIPHER_MODE_CTR) */
#endif
#if defined(POLARSSL_CIPHER_NULL_CIPHER)
case POLARSSL_CIPHER_NULL:
return &null_cipher_info;
#endif /* defined(POLARSSL_CIPHER_NULL_CIPHER) */
default:
return NULL;
}
}
const cipher_info_t *cipher_info_from_string( const char *cipher_name )
{
if( NULL == cipher_name )
return NULL;
/* Get the appropriate cipher information */
#if defined(POLARSSL_CAMELLIA_C)
if( !strcasecmp( "CAMELLIA-128-CBC", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_CAMELLIA_128_CBC );
if( !strcasecmp( "CAMELLIA-192-CBC", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_CAMELLIA_192_CBC );
if( !strcasecmp( "CAMELLIA-256-CBC", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_CAMELLIA_256_CBC );
#if defined(POLARSSL_CIPHER_MODE_CFB)
if( !strcasecmp( "CAMELLIA-128-CFB128", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_CAMELLIA_128_CFB128 );
if( !strcasecmp( "CAMELLIA-192-CFB128", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_CAMELLIA_192_CFB128 );
if( !strcasecmp( "CAMELLIA-256-CFB128", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_CAMELLIA_256_CFB128 );
#endif /* defined(POLARSSL_CIPHER_MODE_CFB) */
#if defined(POLARSSL_CIPHER_MODE_CTR)
if( !strcasecmp( "CAMELLIA-128-CTR", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_CAMELLIA_128_CTR );
if( !strcasecmp( "CAMELLIA-192-CTR", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_CAMELLIA_192_CTR );
if( !strcasecmp( "CAMELLIA-256-CTR", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_CAMELLIA_256_CTR );
#endif /* defined(POLARSSL_CIPHER_MODE_CTR) */
#endif
#if defined(POLARSSL_AES_C)
if( !strcasecmp( "AES-128-CBC", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_AES_128_CBC );
if( !strcasecmp( "AES-192-CBC", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_AES_192_CBC );
if( !strcasecmp( "AES-256-CBC", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_AES_256_CBC );
#if defined(POLARSSL_CIPHER_MODE_CFB)
if( !strcasecmp( "AES-128-CFB128", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_AES_128_CFB128 );
if( !strcasecmp( "AES-192-CFB128", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_AES_192_CFB128 );
if( !strcasecmp( "AES-256-CFB128", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_AES_256_CFB128 );
#endif /* defined(POLARSSL_CIPHER_MODE_CFB) */
#if defined(POLARSSL_CIPHER_MODE_CTR)
if( !strcasecmp( "AES-128-CTR", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_AES_128_CTR );
if( !strcasecmp( "AES-192-CTR", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_AES_192_CTR );
if( !strcasecmp( "AES-256-CTR", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_AES_256_CTR );
#endif /* defined(POLARSSL_CIPHER_MODE_CTR) */
#endif
#if defined(POLARSSL_DES_C)
if( !strcasecmp( "DES-CBC", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_DES_CBC );
if( !strcasecmp( "DES-EDE-CBC", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_DES_EDE_CBC );
if( !strcasecmp( "DES-EDE3-CBC", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_DES_EDE3_CBC );
#endif
#if defined(POLARSSL_BLOWFISH_C)
if( !strcasecmp( "BLOWFISH-CBC", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_BLOWFISH_CBC );
#if defined(POLARSSL_CIPHER_MODE_CFB)
if( !strcasecmp( "BLOWFISH-CFB64", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_BLOWFISH_CFB64 );
#endif /* defined(POLARSSL_CIPHER_MODE_CFB) */
#if defined(POLARSSL_CIPHER_MODE_CTR)
if( !strcasecmp( "BLOWFISH-CTR", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_BLOWFISH_CTR );
#endif /* defined(POLARSSL_CIPHER_MODE_CTR) */
#endif
#if defined(POLARSSL_CIPHER_NULL_CIPHER)
if( !strcasecmp( "NULL", cipher_name ) )
return cipher_info_from_type( POLARSSL_CIPHER_NULL );
#endif /* defined(POLARSSL_CIPHER_NULL_CIPHER) */
return NULL;
}
int cipher_init_ctx( cipher_context_t *ctx, const cipher_info_t *cipher_info )
{
if( NULL == cipher_info || NULL == ctx )
return POLARSSL_ERR_CIPHER_BAD_INPUT_DATA;
memset( ctx, 0, sizeof( cipher_context_t ) );
if( NULL == ( ctx->cipher_ctx = cipher_info->base->ctx_alloc_func() ) )
return POLARSSL_ERR_CIPHER_ALLOC_FAILED;
ctx->cipher_info = cipher_info;
return 0;
}
int cipher_free_ctx( cipher_context_t *ctx )
{
if( ctx == NULL || ctx->cipher_info == NULL )
return POLARSSL_ERR_CIPHER_BAD_INPUT_DATA;
ctx->cipher_info->base->ctx_free_func( ctx->cipher_ctx );
return 0;
}
int cipher_setkey( cipher_context_t *ctx, const unsigned char *key,
int key_length, const operation_t operation )
{
if( NULL == ctx || NULL == ctx->cipher_info )
return POLARSSL_ERR_CIPHER_BAD_INPUT_DATA;
ctx->key_length = key_length;
ctx->operation = operation;
#if defined(POLARSSL_CIPHER_NULL_CIPHER)
if( ctx->cipher_info->mode == POLARSSL_MODE_NULL )
return 0;
#endif /* defined(POLARSSL_CIPHER_NULL_CIPHER) */
/*
* For CFB and CTR mode always use the encryption key schedule
*/
if( POLARSSL_ENCRYPT == operation ||
POLARSSL_MODE_CFB == ctx->cipher_info->mode ||
POLARSSL_MODE_CTR == ctx->cipher_info->mode )
{
return ctx->cipher_info->base->setkey_enc_func( ctx->cipher_ctx, key,
ctx->key_length );
}
if( POLARSSL_DECRYPT == operation )
return ctx->cipher_info->base->setkey_dec_func( ctx->cipher_ctx, key,
ctx->key_length );
return POLARSSL_ERR_CIPHER_BAD_INPUT_DATA;
}
int cipher_reset( cipher_context_t *ctx, const unsigned char *iv )
{
if( NULL == ctx || NULL == ctx->cipher_info || NULL == iv )
return POLARSSL_ERR_CIPHER_BAD_INPUT_DATA;
ctx->unprocessed_len = 0;
memcpy( ctx->iv, iv, cipher_get_iv_size( ctx ) );
return 0;
}
int cipher_update( cipher_context_t *ctx, const unsigned char *input, size_t ilen,
unsigned char *output, size_t *olen )
{
int ret;
size_t copy_len = 0;
if( NULL == ctx || NULL == ctx->cipher_info || NULL == olen ||
input == output )
{
return POLARSSL_ERR_CIPHER_BAD_INPUT_DATA;
}
*olen = 0;
#if defined(POLARSSL_CIPHER_NULL_CIPHER)
if( ctx->cipher_info->mode == POLARSSL_MODE_NULL )
{
memcpy( output, input, ilen );
*olen = ilen;
return 0;
}
#endif /* defined(POLARSSL_CIPHER_NULL_CIPHER) */
if( ctx->cipher_info->mode == POLARSSL_MODE_CBC )
{
/*
* If there is not enough data for a full block, cache it.
*/
if( ( ctx->operation == POLARSSL_DECRYPT &&
ilen + ctx->unprocessed_len <= cipher_get_block_size( ctx ) ) ||
( ctx->operation == POLARSSL_ENCRYPT &&
ilen + ctx->unprocessed_len < cipher_get_block_size( ctx ) ) )
{
memcpy( &( ctx->unprocessed_data[ctx->unprocessed_len] ), input,
ilen );
ctx->unprocessed_len += ilen;
return 0;
}
/*
* Process cached data first
*/
if( ctx->unprocessed_len != 0 )
{
copy_len = cipher_get_block_size( ctx ) - ctx->unprocessed_len;
memcpy( &( ctx->unprocessed_data[ctx->unprocessed_len] ), input,
copy_len );
if( 0 != ( ret = ctx->cipher_info->base->cbc_func( ctx->cipher_ctx,
ctx->operation, cipher_get_block_size( ctx ), ctx->iv,
ctx->unprocessed_data, output ) ) )
{
return ret;
}
*olen += cipher_get_block_size( ctx );
output += cipher_get_block_size( ctx );
ctx->unprocessed_len = 0;
input += copy_len;
ilen -= copy_len;
}
/*
* Cache final, incomplete block
*/
if( 0 != ilen )
{
copy_len = ilen % cipher_get_block_size( ctx );
if( copy_len == 0 && ctx->operation == POLARSSL_DECRYPT )
copy_len = cipher_get_block_size(ctx);
memcpy( ctx->unprocessed_data, &( input[ilen - copy_len] ),
copy_len );
ctx->unprocessed_len += copy_len;
ilen -= copy_len;
}
/*
* Process remaining full blocks
*/
if( ilen )
{
if( 0 != ( ret = ctx->cipher_info->base->cbc_func( ctx->cipher_ctx,
ctx->operation, ilen, ctx->iv, input, output ) ) )
{
return ret;
}
*olen += ilen;
}
return 0;
}
if( ctx->cipher_info->mode == POLARSSL_MODE_CFB )
{
if( 0 != ( ret = ctx->cipher_info->base->cfb_func( ctx->cipher_ctx,
ctx->operation, ilen, &ctx->unprocessed_len, ctx->iv,
input, output ) ) )
{
return ret;
}
*olen = ilen;
return 0;
}
if( ctx->cipher_info->mode == POLARSSL_MODE_CTR )
{
if( 0 != ( ret = ctx->cipher_info->base->ctr_func( ctx->cipher_ctx,
ilen, &ctx->unprocessed_len, ctx->iv,
ctx->unprocessed_data, input, output ) ) )
{
return ret;
}
*olen = ilen;
return 0;
}
return POLARSSL_ERR_CIPHER_FEATURE_UNAVAILABLE;
}
static void add_pkcs_padding( unsigned char *output, size_t output_len,
size_t data_len )
{
size_t padding_len = output_len - data_len;
unsigned char i = 0;
for( i = 0; i < padding_len; i++ )
output[data_len + i] = (unsigned char) padding_len;
}
static int get_pkcs_padding( unsigned char *input, unsigned int input_len,
size_t *data_len)
{
unsigned int i, padding_len = 0;
if( NULL == input || NULL == data_len )
return POLARSSL_ERR_CIPHER_BAD_INPUT_DATA;
padding_len = input[input_len - 1];
if( padding_len > input_len )
return POLARSSL_ERR_CIPHER_INVALID_PADDING;
for( i = input_len - padding_len; i < input_len; i++ )
if( input[i] != padding_len )
return POLARSSL_ERR_CIPHER_INVALID_PADDING;
*data_len = input_len - padding_len;
return 0;
}
int cipher_finish( cipher_context_t *ctx, unsigned char *output, size_t *olen)
{
int ret = 0;
if( NULL == ctx || NULL == ctx->cipher_info || NULL == olen )
return POLARSSL_ERR_CIPHER_BAD_INPUT_DATA;
*olen = 0;
if( POLARSSL_MODE_CFB == ctx->cipher_info->mode ||
POLARSSL_MODE_CTR == ctx->cipher_info->mode ||
POLARSSL_MODE_NULL == ctx->cipher_info->mode )
{
return 0;
}
if( POLARSSL_MODE_CBC == ctx->cipher_info->mode )
{
if( POLARSSL_ENCRYPT == ctx->operation )
{
add_pkcs_padding( ctx->unprocessed_data, cipher_get_iv_size( ctx ),
ctx->unprocessed_len );
}
else if ( cipher_get_block_size( ctx ) != ctx->unprocessed_len )
{
/* For decrypt operations, expect a full block */
return POLARSSL_ERR_CIPHER_FULL_BLOCK_EXPECTED;
}
/* cipher block */
if( 0 != ( ret = ctx->cipher_info->base->cbc_func( ctx->cipher_ctx,
ctx->operation, cipher_get_block_size( ctx ), ctx->iv,
ctx->unprocessed_data, output ) ) )
{
return ret;
}
/* Set output size for decryption */
if( POLARSSL_DECRYPT == ctx->operation )
return get_pkcs_padding( output, cipher_get_block_size( ctx ), olen );
/* Set output size for encryption */
*olen = cipher_get_block_size( ctx );
return 0;
}
return POLARSSL_ERR_CIPHER_FEATURE_UNAVAILABLE;
}
#if defined(POLARSSL_SELF_TEST)
#include <stdio.h>
#define ASSERT(x) if (!(x)) { \
printf( "failed with %i at %s\n", value, (#x) ); \
return( 1 ); \
}
/*
* Checkup routine
*/
int cipher_self_test( int verbose )
{
((void) verbose);
return( 0 );
}
#endif
#endif
-711
View File
@@ -1,711 +0,0 @@
/**
* \file md_wrap.c
*
* \brief Generic cipher wrapper for PolarSSL
*
* \author Adriaan de Jong <dejong@fox-it.com>
*
* Copyright (C) 2006-2012, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_CIPHER_C)
#include "polarssl/cipher_wrap.h"
#if defined(POLARSSL_AES_C)
#include "polarssl/aes.h"
#endif
#if defined(POLARSSL_CAMELLIA_C)
#include "polarssl/camellia.h"
#endif
#if defined(POLARSSL_DES_C)
#include "polarssl/des.h"
#endif
#if defined(POLARSSL_BLOWFISH_C)
#include "polarssl/blowfish.h"
#endif
#include <stdlib.h>
#if defined(POLARSSL_AES_C)
int aes_crypt_cbc_wrap( void *ctx, operation_t operation, size_t length,
unsigned char *iv, const unsigned char *input, unsigned char *output )
{
return aes_crypt_cbc( (aes_context *) ctx, operation, length, iv, input, output );
}
int aes_crypt_cfb128_wrap( void *ctx, operation_t operation, size_t length,
size_t *iv_off, unsigned char *iv, const unsigned char *input, unsigned char *output )
{
#if defined(POLARSSL_CIPHER_MODE_CFB)
return aes_crypt_cfb128( (aes_context *) ctx, operation, length, iv_off, iv, input, output );
#else
((void) ctx);
((void) operation);
((void) length);
((void) iv_off);
((void) iv);
((void) input);
((void) output);
return POLARSSL_ERR_CIPHER_FEATURE_UNAVAILABLE;
#endif
}
int aes_crypt_ctr_wrap( void *ctx, size_t length,
size_t *nc_off, unsigned char *nonce_counter, unsigned char *stream_block,
const unsigned char *input, unsigned char *output )
{
#if defined(POLARSSL_CIPHER_MODE_CTR)
return aes_crypt_ctr( (aes_context *) ctx, length, nc_off, nonce_counter,
stream_block, input, output );
#else
((void) ctx);
((void) length);
((void) nc_off);
((void) nonce_counter);
((void) stream_block);
((void) input);
((void) output);
return POLARSSL_ERR_CIPHER_FEATURE_UNAVAILABLE;
#endif
}
int aes_setkey_dec_wrap( void *ctx, const unsigned char *key, unsigned int key_length )
{
return aes_setkey_dec( (aes_context *) ctx, key, key_length );
}
int aes_setkey_enc_wrap( void *ctx, const unsigned char *key, unsigned int key_length )
{
return aes_setkey_enc( (aes_context *) ctx, key, key_length );
}
static void * aes_ctx_alloc( void )
{
return malloc( sizeof( aes_context ) );
}
static void aes_ctx_free( void *ctx )
{
free( ctx );
}
const cipher_base_t aes_info = {
POLARSSL_CIPHER_ID_AES,
aes_crypt_cbc_wrap,
aes_crypt_cfb128_wrap,
aes_crypt_ctr_wrap,
aes_setkey_enc_wrap,
aes_setkey_dec_wrap,
aes_ctx_alloc,
aes_ctx_free
};
const cipher_info_t aes_128_cbc_info = {
POLARSSL_CIPHER_AES_128_CBC,
POLARSSL_MODE_CBC,
128,
"AES-128-CBC",
16,
16,
&aes_info
};
const cipher_info_t aes_192_cbc_info = {
POLARSSL_CIPHER_AES_192_CBC,
POLARSSL_MODE_CBC,
192,
"AES-192-CBC",
16,
16,
&aes_info
};
const cipher_info_t aes_256_cbc_info = {
POLARSSL_CIPHER_AES_256_CBC,
POLARSSL_MODE_CBC,
256,
"AES-256-CBC",
16,
16,
&aes_info
};
#if defined(POLARSSL_CIPHER_MODE_CFB)
const cipher_info_t aes_128_cfb128_info = {
POLARSSL_CIPHER_AES_128_CFB128,
POLARSSL_MODE_CFB,
128,
"AES-128-CFB128",
16,
16,
&aes_info
};
const cipher_info_t aes_192_cfb128_info = {
POLARSSL_CIPHER_AES_192_CFB128,
POLARSSL_MODE_CFB,
192,
"AES-192-CFB128",
16,
16,
&aes_info
};
const cipher_info_t aes_256_cfb128_info = {
POLARSSL_CIPHER_AES_256_CFB128,
POLARSSL_MODE_CFB,
256,
"AES-256-CFB128",
16,
16,
&aes_info
};
#endif /* POLARSSL_CIPHER_MODE_CFB */
#if defined(POLARSSL_CIPHER_MODE_CTR)
const cipher_info_t aes_128_ctr_info = {
POLARSSL_CIPHER_AES_128_CTR,
POLARSSL_MODE_CTR,
128,
"AES-128-CTR",
16,
16,
&aes_info
};
const cipher_info_t aes_192_ctr_info = {
POLARSSL_CIPHER_AES_192_CTR,
POLARSSL_MODE_CTR,
192,
"AES-192-CTR",
16,
16,
&aes_info
};
const cipher_info_t aes_256_ctr_info = {
POLARSSL_CIPHER_AES_256_CTR,
POLARSSL_MODE_CTR,
256,
"AES-256-CTR",
16,
16,
&aes_info
};
#endif /* POLARSSL_CIPHER_MODE_CTR */
#endif
#if defined(POLARSSL_CAMELLIA_C)
int camellia_crypt_cbc_wrap( void *ctx, operation_t operation, size_t length,
unsigned char *iv, const unsigned char *input, unsigned char *output )
{
return camellia_crypt_cbc( (camellia_context *) ctx, operation, length, iv, input, output );
}
int camellia_crypt_cfb128_wrap( void *ctx, operation_t operation, size_t length,
size_t *iv_off, unsigned char *iv, const unsigned char *input, unsigned char *output )
{
#if defined(POLARSSL_CIPHER_MODE_CFB)
return camellia_crypt_cfb128( (camellia_context *) ctx, operation, length, iv_off, iv, input, output );
#else
((void) ctx);
((void) operation);
((void) length);
((void) iv_off);
((void) iv);
((void) input);
((void) output);
return POLARSSL_ERR_CIPHER_FEATURE_UNAVAILABLE;
#endif
}
int camellia_crypt_ctr_wrap( void *ctx, size_t length,
size_t *nc_off, unsigned char *nonce_counter, unsigned char *stream_block,
const unsigned char *input, unsigned char *output )
{
#if defined(POLARSSL_CIPHER_MODE_CTR)
return camellia_crypt_ctr( (camellia_context *) ctx, length, nc_off, nonce_counter,
stream_block, input, output );
#else
((void) ctx);
((void) length);
((void) nc_off);
((void) nonce_counter);
((void) stream_block);
((void) input);
((void) output);
return POLARSSL_ERR_CIPHER_FEATURE_UNAVAILABLE;
#endif
}
int camellia_setkey_dec_wrap( void *ctx, const unsigned char *key, unsigned int key_length )
{
return camellia_setkey_dec( (camellia_context *) ctx, key, key_length );
}
int camellia_setkey_enc_wrap( void *ctx, const unsigned char *key, unsigned int key_length )
{
return camellia_setkey_enc( (camellia_context *) ctx, key, key_length );
}
static void * camellia_ctx_alloc( void )
{
return malloc( sizeof( camellia_context ) );
}
static void camellia_ctx_free( void *ctx )
{
free( ctx );
}
const cipher_base_t camellia_info = {
POLARSSL_CIPHER_ID_CAMELLIA,
camellia_crypt_cbc_wrap,
camellia_crypt_cfb128_wrap,
camellia_crypt_ctr_wrap,
camellia_setkey_enc_wrap,
camellia_setkey_dec_wrap,
camellia_ctx_alloc,
camellia_ctx_free
};
const cipher_info_t camellia_128_cbc_info = {
POLARSSL_CIPHER_CAMELLIA_128_CBC,
POLARSSL_MODE_CBC,
128,
"CAMELLIA-128-CBC",
16,
16,
&camellia_info
};
const cipher_info_t camellia_192_cbc_info = {
POLARSSL_CIPHER_CAMELLIA_192_CBC,
POLARSSL_MODE_CBC,
192,
"CAMELLIA-192-CBC",
16,
16,
&camellia_info
};
const cipher_info_t camellia_256_cbc_info = {
POLARSSL_CIPHER_CAMELLIA_256_CBC,
POLARSSL_MODE_CBC,
256,
"CAMELLIA-256-CBC",
16,
16,
&camellia_info
};
#if defined(POLARSSL_CIPHER_MODE_CFB)
const cipher_info_t camellia_128_cfb128_info = {
POLARSSL_CIPHER_CAMELLIA_128_CFB128,
POLARSSL_MODE_CFB,
128,
"CAMELLIA-128-CFB128",
16,
16,
&camellia_info
};
const cipher_info_t camellia_192_cfb128_info = {
POLARSSL_CIPHER_CAMELLIA_192_CFB128,
POLARSSL_MODE_CFB,
192,
"CAMELLIA-192-CFB128",
16,
16,
&camellia_info
};
const cipher_info_t camellia_256_cfb128_info = {
POLARSSL_CIPHER_CAMELLIA_256_CFB128,
POLARSSL_MODE_CFB,
256,
"CAMELLIA-256-CFB128",
16,
16,
&camellia_info
};
#endif /* POLARSSL_CIPHER_MODE_CFB */
#if defined(POLARSSL_CIPHER_MODE_CTR)
const cipher_info_t camellia_128_ctr_info = {
POLARSSL_CIPHER_CAMELLIA_128_CTR,
POLARSSL_MODE_CTR,
128,
"CAMELLIA-128-CTR",
16,
16,
&camellia_info
};
const cipher_info_t camellia_192_ctr_info = {
POLARSSL_CIPHER_CAMELLIA_192_CTR,
POLARSSL_MODE_CTR,
192,
"CAMELLIA-192-CTR",
16,
16,
&camellia_info
};
const cipher_info_t camellia_256_ctr_info = {
POLARSSL_CIPHER_CAMELLIA_256_CTR,
POLARSSL_MODE_CTR,
256,
"CAMELLIA-256-CTR",
16,
16,
&camellia_info
};
#endif /* POLARSSL_CIPHER_MODE_CTR */
#endif
#if defined(POLARSSL_DES_C)
int des_crypt_cbc_wrap( void *ctx, operation_t operation, size_t length,
unsigned char *iv, const unsigned char *input, unsigned char *output )
{
return des_crypt_cbc( (des_context *) ctx, operation, length, iv, input, output );
}
int des3_crypt_cbc_wrap( void *ctx, operation_t operation, size_t length,
unsigned char *iv, const unsigned char *input, unsigned char *output )
{
return des3_crypt_cbc( (des3_context *) ctx, operation, length, iv, input, output );
}
int des_crypt_cfb128_wrap( void *ctx, operation_t operation, size_t length,
size_t *iv_off, unsigned char *iv, const unsigned char *input, unsigned char *output )
{
((void) ctx);
((void) operation);
((void) length);
((void) iv_off);
((void) iv);
((void) input);
((void) output);
return POLARSSL_ERR_CIPHER_FEATURE_UNAVAILABLE;
}
int des_crypt_ctr_wrap( void *ctx, size_t length,
size_t *nc_off, unsigned char *nonce_counter, unsigned char *stream_block,
const unsigned char *input, unsigned char *output )
{
((void) ctx);
((void) length);
((void) nc_off);
((void) nonce_counter);
((void) stream_block);
((void) input);
((void) output);
return POLARSSL_ERR_CIPHER_FEATURE_UNAVAILABLE;
}
int des_setkey_dec_wrap( void *ctx, const unsigned char *key, unsigned int key_length )
{
((void) key_length);
return des_setkey_dec( (des_context *) ctx, key );
}
int des_setkey_enc_wrap( void *ctx, const unsigned char *key, unsigned int key_length )
{
((void) key_length);
return des_setkey_enc( (des_context *) ctx, key );
}
int des3_set2key_dec_wrap( void *ctx, const unsigned char *key, unsigned int key_length )
{
((void) key_length);
return des3_set2key_dec( (des3_context *) ctx, key );
}
int des3_set2key_enc_wrap( void *ctx, const unsigned char *key, unsigned int key_length )
{
((void) key_length);
return des3_set2key_enc( (des3_context *) ctx, key );
}
int des3_set3key_dec_wrap( void *ctx, const unsigned char *key, unsigned int key_length )
{
((void) key_length);
return des3_set3key_dec( (des3_context *) ctx, key );
}
int des3_set3key_enc_wrap( void *ctx, const unsigned char *key, unsigned int key_length )
{
((void) key_length);
return des3_set3key_enc( (des3_context *) ctx, key );
}
static void * des_ctx_alloc( void )
{
return malloc( sizeof( des_context ) );
}
static void * des3_ctx_alloc( void )
{
return malloc( sizeof( des3_context ) );
}
static void des_ctx_free( void *ctx )
{
free( ctx );
}
const cipher_base_t des_info = {
POLARSSL_CIPHER_ID_DES,
des_crypt_cbc_wrap,
des_crypt_cfb128_wrap,
des_crypt_ctr_wrap,
des_setkey_enc_wrap,
des_setkey_dec_wrap,
des_ctx_alloc,
des_ctx_free
};
const cipher_info_t des_cbc_info = {
POLARSSL_CIPHER_DES_CBC,
POLARSSL_MODE_CBC,
POLARSSL_KEY_LENGTH_DES,
"DES-CBC",
8,
8,
&des_info
};
const cipher_base_t des_ede_info = {
POLARSSL_CIPHER_ID_DES,
des3_crypt_cbc_wrap,
des_crypt_cfb128_wrap,
des_crypt_ctr_wrap,
des3_set2key_enc_wrap,
des3_set2key_dec_wrap,
des3_ctx_alloc,
des_ctx_free
};
const cipher_info_t des_ede_cbc_info = {
POLARSSL_CIPHER_DES_EDE_CBC,
POLARSSL_MODE_CBC,
POLARSSL_KEY_LENGTH_DES_EDE,
"DES-EDE-CBC",
8,
8,
&des_ede_info
};
const cipher_base_t des_ede3_info = {
POLARSSL_CIPHER_ID_DES,
des3_crypt_cbc_wrap,
des_crypt_cfb128_wrap,
des_crypt_ctr_wrap,
des3_set3key_enc_wrap,
des3_set3key_dec_wrap,
des3_ctx_alloc,
des_ctx_free
};
const cipher_info_t des_ede3_cbc_info = {
POLARSSL_CIPHER_DES_EDE3_CBC,
POLARSSL_MODE_CBC,
POLARSSL_KEY_LENGTH_DES_EDE3,
"DES-EDE3-CBC",
8,
8,
&des_ede3_info
};
#endif
#if defined(POLARSSL_BLOWFISH_C)
int blowfish_crypt_cbc_wrap( void *ctx, operation_t operation, size_t length,
unsigned char *iv, const unsigned char *input, unsigned char *output )
{
return blowfish_crypt_cbc( (blowfish_context *) ctx, operation, length, iv, input, output );
}
int blowfish_crypt_cfb64_wrap( void *ctx, operation_t operation, size_t length,
size_t *iv_off, unsigned char *iv, const unsigned char *input, unsigned char *output )
{
#if defined(POLARSSL_CIPHER_MODE_CFB)
return blowfish_crypt_cfb64( (blowfish_context *) ctx, operation, length, iv_off, iv, input, output );
#else
((void) ctx);
((void) operation);
((void) length);
((void) iv_off);
((void) iv);
((void) input);
((void) output);
return POLARSSL_ERR_CIPHER_FEATURE_UNAVAILABLE;
#endif
}
int blowfish_crypt_ctr_wrap( void *ctx, size_t length,
size_t *nc_off, unsigned char *nonce_counter, unsigned char *stream_block,
const unsigned char *input, unsigned char *output )
{
#if defined(POLARSSL_CIPHER_MODE_CTR)
return blowfish_crypt_ctr( (blowfish_context *) ctx, length, nc_off, nonce_counter,
stream_block, input, output );
#else
((void) ctx);
((void) length);
((void) nc_off);
((void) nonce_counter);
((void) stream_block);
((void) input);
((void) output);
return POLARSSL_ERR_CIPHER_FEATURE_UNAVAILABLE;
#endif
}
int blowfish_setkey_dec_wrap( void *ctx, const unsigned char *key, unsigned int key_length )
{
return blowfish_setkey( (blowfish_context *) ctx, key, key_length );
}
int blowfish_setkey_enc_wrap( void *ctx, const unsigned char *key, unsigned int key_length )
{
return blowfish_setkey( (blowfish_context *) ctx, key, key_length );
}
static void * blowfish_ctx_alloc( void )
{
return malloc( sizeof( blowfish_context ) );
}
static void blowfish_ctx_free( void *ctx )
{
free( ctx );
}
const cipher_base_t blowfish_info = {
POLARSSL_CIPHER_ID_BLOWFISH,
blowfish_crypt_cbc_wrap,
blowfish_crypt_cfb64_wrap,
blowfish_crypt_ctr_wrap,
blowfish_setkey_enc_wrap,
blowfish_setkey_dec_wrap,
blowfish_ctx_alloc,
blowfish_ctx_free
};
const cipher_info_t blowfish_cbc_info = {
POLARSSL_CIPHER_BLOWFISH_CBC,
POLARSSL_MODE_CBC,
128,
"BLOWFISH-CBC",
8,
8,
&blowfish_info
};
#if defined(POLARSSL_CIPHER_MODE_CFB)
const cipher_info_t blowfish_cfb64_info = {
POLARSSL_CIPHER_BLOWFISH_CFB64,
POLARSSL_MODE_CFB,
128,
"BLOWFISH-CFB64",
8,
8,
&blowfish_info
};
#endif /* POLARSSL_CIPHER_MODE_CFB */
#if defined(POLARSSL_CIPHER_MODE_CTR)
const cipher_info_t blowfish_ctr_info = {
POLARSSL_CIPHER_BLOWFISH_CTR,
POLARSSL_MODE_CTR,
128,
"BLOWFISH-CTR",
8,
8,
&blowfish_info
};
#endif /* POLARSSL_CIPHER_MODE_CTR */
#endif /* POLARSSL_BLOWFISH_C */
#if defined(POLARSSL_CIPHER_NULL_CIPHER)
static void * null_ctx_alloc( void )
{
return (void *) 1;
}
static void null_ctx_free( void *ctx )
{
((void) ctx);
}
const cipher_base_t null_base_info = {
POLARSSL_CIPHER_ID_NULL,
NULL,
NULL,
NULL,
NULL,
NULL,
null_ctx_alloc,
null_ctx_free
};
const cipher_info_t null_cipher_info = {
POLARSSL_CIPHER_NULL,
POLARSSL_MODE_NULL,
0,
"NULL",
1,
1,
&null_base_info
};
#endif /* defined(POLARSSL_CIPHER_NULL_CIPHER) */
#endif
-562
View File
@@ -1,562 +0,0 @@
/*
* CTR_DRBG implementation based on AES-256 (NIST SP 800-90)
*
* Copyright (C) 2006-2011, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*
* The NIST SP 800-90 DRBGs are described in the following publucation.
*
* http://csrc.nist.gov/publications/nistpubs/800-90/SP800-90revised_March2007.pdf
*/
#include "polarssl/config.h"
#if defined(POLARSSL_CTR_DRBG_C)
#include "polarssl/ctr_drbg.h"
#if defined(POLARSSL_FS_IO)
#include <stdio.h>
#endif
/*
* Non-public function wrapped by ctr_crbg_init(). Necessary to allow NIST
* tests to succeed (which require known length fixed entropy)
*/
int ctr_drbg_init_entropy_len(
ctr_drbg_context *ctx,
int (*f_entropy)(void *, unsigned char *, size_t),
void *p_entropy,
const unsigned char *custom,
size_t len,
size_t entropy_len )
{
int ret;
unsigned char key[CTR_DRBG_KEYSIZE];
memset( ctx, 0, sizeof(ctr_drbg_context) );
memset( key, 0, CTR_DRBG_KEYSIZE );
ctx->f_entropy = f_entropy;
ctx->p_entropy = p_entropy;
ctx->entropy_len = entropy_len;
ctx->reseed_interval = CTR_DRBG_RESEED_INTERVAL;
/*
* Initialize with an empty key
*/
aes_setkey_enc( &ctx->aes_ctx, key, CTR_DRBG_KEYBITS );
if( ( ret = ctr_drbg_reseed( ctx, custom, len ) ) != 0 )
return( ret );
return( 0 );
}
int ctr_drbg_init( ctr_drbg_context *ctx,
int (*f_entropy)(void *, unsigned char *, size_t),
void *p_entropy,
const unsigned char *custom,
size_t len )
{
return( ctr_drbg_init_entropy_len( ctx, f_entropy, p_entropy, custom, len,
CTR_DRBG_ENTROPY_LEN ) );
}
void ctr_drbg_set_prediction_resistance( ctr_drbg_context *ctx, int resistance )
{
ctx->prediction_resistance = resistance;
}
void ctr_drbg_set_entropy_len( ctr_drbg_context *ctx, size_t len )
{
ctx->entropy_len = len;
}
void ctr_drbg_set_reseed_interval( ctr_drbg_context *ctx, int interval )
{
ctx->reseed_interval = interval;
}
int block_cipher_df( unsigned char *output,
const unsigned char *data, size_t data_len )
{
unsigned char buf[CTR_DRBG_MAX_SEED_INPUT + CTR_DRBG_BLOCKSIZE + 16];
unsigned char tmp[CTR_DRBG_SEEDLEN];
unsigned char key[CTR_DRBG_KEYSIZE];
unsigned char chain[CTR_DRBG_BLOCKSIZE];
unsigned char *p = buf, *iv;
aes_context aes_ctx;
int i, j, buf_len, use_len;
memset( buf, 0, CTR_DRBG_MAX_SEED_INPUT + CTR_DRBG_BLOCKSIZE + 16 );
/*
* Construct IV (16 bytes) and S in buffer
* IV = Counter (in 32-bits) padded to 16 with zeroes
* S = Length input string (in 32-bits) || Length of output (in 32-bits) ||
* data || 0x80
* (Total is padded to a multiple of 16-bytes with zeroes)
*/
p = buf + CTR_DRBG_BLOCKSIZE;
*p++ = ( data_len >> 24 ) & 0xff;
*p++ = ( data_len >> 16 ) & 0xff;
*p++ = ( data_len >> 8 ) & 0xff;
*p++ = ( data_len ) & 0xff;
p += 3;
*p++ = CTR_DRBG_SEEDLEN;
memcpy( p, data, data_len );
p[data_len] = 0x80;
buf_len = CTR_DRBG_BLOCKSIZE + 8 + data_len + 1;
for( i = 0; i < CTR_DRBG_KEYSIZE; i++ )
key[i] = i;
aes_setkey_enc( &aes_ctx, key, CTR_DRBG_KEYBITS );
/*
* Reduce data to POLARSSL_CTR_DRBG_SEEDLEN bytes of data
*/
for( j = 0; j < CTR_DRBG_SEEDLEN; j += CTR_DRBG_BLOCKSIZE )
{
p = buf;
memset( chain, 0, CTR_DRBG_BLOCKSIZE );
use_len = buf_len;
while( use_len > 0 )
{
for( i = 0; i < CTR_DRBG_BLOCKSIZE; i++ )
chain[i] ^= p[i];
p += CTR_DRBG_BLOCKSIZE;
use_len -= CTR_DRBG_BLOCKSIZE;
aes_crypt_ecb( &aes_ctx, AES_ENCRYPT, chain, chain );
}
memcpy( tmp + j, chain, CTR_DRBG_BLOCKSIZE );
/*
* Update IV
*/
buf[3]++;
}
/*
* Do final encryption with reduced data
*/
aes_setkey_enc( &aes_ctx, tmp, CTR_DRBG_KEYBITS );
iv = tmp + CTR_DRBG_KEYSIZE;
p = output;
for( j = 0; j < CTR_DRBG_SEEDLEN; j += CTR_DRBG_BLOCKSIZE )
{
aes_crypt_ecb( &aes_ctx, AES_ENCRYPT, iv, iv );
memcpy( p, iv, CTR_DRBG_BLOCKSIZE );
p += CTR_DRBG_BLOCKSIZE;
}
return( 0 );
}
int ctr_drbg_update_internal( ctr_drbg_context *ctx,
const unsigned char data[CTR_DRBG_SEEDLEN] )
{
unsigned char tmp[CTR_DRBG_SEEDLEN];
unsigned char *p = tmp;
int i, j;
memset( tmp, 0, CTR_DRBG_SEEDLEN );
for( j = 0; j < CTR_DRBG_SEEDLEN; j += CTR_DRBG_BLOCKSIZE )
{
/*
* Increase counter
*/
for( i = CTR_DRBG_BLOCKSIZE; i > 0; i-- )
if( ++ctx->counter[i - 1] != 0 )
break;
/*
* Crypt counter block
*/
aes_crypt_ecb( &ctx->aes_ctx, AES_ENCRYPT, ctx->counter, p );
p += CTR_DRBG_BLOCKSIZE;
}
for( i = 0; i < CTR_DRBG_SEEDLEN; i++ )
tmp[i] ^= data[i];
/*
* Update key and counter
*/
aes_setkey_enc( &ctx->aes_ctx, tmp, CTR_DRBG_KEYBITS );
memcpy( ctx->counter, tmp + CTR_DRBG_KEYSIZE, CTR_DRBG_BLOCKSIZE );
return( 0 );
}
void ctr_drbg_update( ctr_drbg_context *ctx,
const unsigned char *additional, size_t add_len )
{
unsigned char add_input[CTR_DRBG_SEEDLEN];
if( add_len > 0 )
{
block_cipher_df( add_input, additional, add_len );
ctr_drbg_update_internal( ctx, add_input );
}
}
int ctr_drbg_reseed( ctr_drbg_context *ctx,
const unsigned char *additional, size_t len )
{
unsigned char seed[CTR_DRBG_MAX_SEED_INPUT];
size_t seedlen = 0;
if( ctx->entropy_len + len > CTR_DRBG_MAX_SEED_INPUT )
return( POLARSSL_ERR_CTR_DRBG_INPUT_TOO_BIG );
memset( seed, 0, CTR_DRBG_MAX_SEED_INPUT );
/*
* Gather enropy_len bytes of entropy to seed state
*/
if( 0 != ctx->f_entropy( ctx->p_entropy, seed,
ctx->entropy_len ) )
{
return( POLARSSL_ERR_CTR_DRBG_ENTROPY_SOURCE_FAILED );
}
seedlen += ctx->entropy_len;
/*
* Add additional data
*/
if( additional && len )
{
memcpy( seed + seedlen, additional, len );
seedlen += len;
}
/*
* Reduce to 384 bits
*/
block_cipher_df( seed, seed, seedlen );
/*
* Update state
*/
ctr_drbg_update_internal( ctx, seed );
ctx->reseed_counter = 1;
return( 0 );
}
int ctr_drbg_random_with_add( void *p_rng,
unsigned char *output, size_t output_len,
const unsigned char *additional, size_t add_len )
{
int ret = 0;
ctr_drbg_context *ctx = (ctr_drbg_context *) p_rng;
unsigned char add_input[CTR_DRBG_SEEDLEN];
unsigned char *p = output;
unsigned char tmp[CTR_DRBG_BLOCKSIZE];
int i;
size_t use_len;
if( output_len > CTR_DRBG_MAX_REQUEST )
return( POLARSSL_ERR_CTR_DRBG_REQUEST_TOO_BIG );
if( add_len > CTR_DRBG_MAX_INPUT )
return( POLARSSL_ERR_CTR_DRBG_INPUT_TOO_BIG );
memset( add_input, 0, CTR_DRBG_SEEDLEN );
if( ctx->reseed_counter > ctx->reseed_interval ||
ctx->prediction_resistance )
{
if( ( ret = ctr_drbg_reseed( ctx, additional, add_len ) ) != 0 )
return( ret );
add_len = 0;
}
if( add_len > 0 )
{
block_cipher_df( add_input, additional, add_len );
ctr_drbg_update_internal( ctx, add_input );
}
while( output_len > 0 )
{
/*
* Increase counter
*/
for( i = CTR_DRBG_BLOCKSIZE; i > 0; i-- )
if( ++ctx->counter[i - 1] != 0 )
break;
/*
* Crypt counter block
*/
aes_crypt_ecb( &ctx->aes_ctx, AES_ENCRYPT, ctx->counter, tmp );
use_len = (output_len > CTR_DRBG_BLOCKSIZE ) ? CTR_DRBG_BLOCKSIZE : output_len;
/*
* Copy random block to destination
*/
memcpy( p, tmp, use_len );
p += use_len;
output_len -= use_len;
}
ctr_drbg_update_internal( ctx, add_input );
ctx->reseed_counter++;
return( 0 );
}
int ctr_drbg_random( void *p_rng, unsigned char *output, size_t output_len )
{
return ctr_drbg_random_with_add( p_rng, output, output_len, NULL, 0 );
}
#if defined(POLARSSL_FS_IO)
int ctr_drbg_write_seed_file( ctr_drbg_context *ctx, const char *path )
{
int ret;
FILE *f;
unsigned char buf[ CTR_DRBG_MAX_INPUT ];
if( ( f = fopen( path, "wb" ) ) == NULL )
return( POLARSSL_ERR_CTR_DRBG_FILE_IO_ERROR );
if( ( ret = ctr_drbg_random( ctx, buf, CTR_DRBG_MAX_INPUT ) ) != 0 )
return( ret );
if( fwrite( buf, 1, CTR_DRBG_MAX_INPUT, f ) != CTR_DRBG_MAX_INPUT )
{
fclose( f );
return( POLARSSL_ERR_CTR_DRBG_FILE_IO_ERROR );
}
fclose( f );
return( 0 );
}
int ctr_drbg_update_seed_file( ctr_drbg_context *ctx, const char *path )
{
FILE *f;
size_t n;
unsigned char buf[ CTR_DRBG_MAX_INPUT ];
if( ( f = fopen( path, "rb" ) ) == NULL )
return( POLARSSL_ERR_CTR_DRBG_FILE_IO_ERROR );
fseek( f, 0, SEEK_END );
n = (size_t) ftell( f );
fseek( f, 0, SEEK_SET );
if( n > CTR_DRBG_MAX_INPUT )
return( POLARSSL_ERR_CTR_DRBG_INPUT_TOO_BIG );
if( fread( buf, 1, n, f ) != n )
{
fclose( f );
return( POLARSSL_ERR_CTR_DRBG_FILE_IO_ERROR );
}
ctr_drbg_update( ctx, buf, n );
fclose( f );
return( ctr_drbg_write_seed_file( ctx, path ) );
}
#endif /* POLARSSL_FS_IO */
#if defined(POLARSSL_SELF_TEST)
#include <stdio.h>
unsigned char entropy_source_pr[96] =
{ 0xc1, 0x80, 0x81, 0xa6, 0x5d, 0x44, 0x02, 0x16,
0x19, 0xb3, 0xf1, 0x80, 0xb1, 0xc9, 0x20, 0x02,
0x6a, 0x54, 0x6f, 0x0c, 0x70, 0x81, 0x49, 0x8b,
0x6e, 0xa6, 0x62, 0x52, 0x6d, 0x51, 0xb1, 0xcb,
0x58, 0x3b, 0xfa, 0xd5, 0x37, 0x5f, 0xfb, 0xc9,
0xff, 0x46, 0xd2, 0x19, 0xc7, 0x22, 0x3e, 0x95,
0x45, 0x9d, 0x82, 0xe1, 0xe7, 0x22, 0x9f, 0x63,
0x31, 0x69, 0xd2, 0x6b, 0x57, 0x47, 0x4f, 0xa3,
0x37, 0xc9, 0x98, 0x1c, 0x0b, 0xfb, 0x91, 0x31,
0x4d, 0x55, 0xb9, 0xe9, 0x1c, 0x5a, 0x5e, 0xe4,
0x93, 0x92, 0xcf, 0xc5, 0x23, 0x12, 0xd5, 0x56,
0x2c, 0x4a, 0x6e, 0xff, 0xdc, 0x10, 0xd0, 0x68 };
unsigned char entropy_source_nopr[64] =
{ 0x5a, 0x19, 0x4d, 0x5e, 0x2b, 0x31, 0x58, 0x14,
0x54, 0xde, 0xf6, 0x75, 0xfb, 0x79, 0x58, 0xfe,
0xc7, 0xdb, 0x87, 0x3e, 0x56, 0x89, 0xfc, 0x9d,
0x03, 0x21, 0x7c, 0x68, 0xd8, 0x03, 0x38, 0x20,
0xf9, 0xe6, 0x5e, 0x04, 0xd8, 0x56, 0xf3, 0xa9,
0xc4, 0x4a, 0x4c, 0xbd, 0xc1, 0xd0, 0x08, 0x46,
0xf5, 0x98, 0x3d, 0x77, 0x1c, 0x1b, 0x13, 0x7e,
0x4e, 0x0f, 0x9d, 0x8e, 0xf4, 0x09, 0xf9, 0x2e };
unsigned char nonce_pers_pr[16] =
{ 0xd2, 0x54, 0xfc, 0xff, 0x02, 0x1e, 0x69, 0xd2,
0x29, 0xc9, 0xcf, 0xad, 0x85, 0xfa, 0x48, 0x6c };
unsigned char nonce_pers_nopr[16] =
{ 0x1b, 0x54, 0xb8, 0xff, 0x06, 0x42, 0xbf, 0xf5,
0x21, 0xf1, 0x5c, 0x1c, 0x0b, 0x66, 0x5f, 0x3f };
unsigned char result_pr[16] =
{ 0x34, 0x01, 0x16, 0x56, 0xb4, 0x29, 0x00, 0x8f,
0x35, 0x63, 0xec, 0xb5, 0xf2, 0x59, 0x07, 0x23 };
unsigned char result_nopr[16] =
{ 0xa0, 0x54, 0x30, 0x3d, 0x8a, 0x7e, 0xa9, 0x88,
0x9d, 0x90, 0x3e, 0x07, 0x7c, 0x6f, 0x21, 0x8f };
int test_offset;
int ctr_drbg_self_test_entropy( void *data, unsigned char *buf, size_t len )
{
unsigned char *p = data;
memcpy( buf, p + test_offset, len );
test_offset += 32;
return( 0 );
}
/*
* Checkup routine
*/
int ctr_drbg_self_test( int verbose )
{
ctr_drbg_context ctx;
unsigned char buf[16];
/*
* Based on a NIST CTR_DRBG test vector (PR = True)
*/
if( verbose != 0 )
printf( " CTR_DRBG (PR = TRUE) : " );
test_offset = 0;
if( ctr_drbg_init_entropy_len( &ctx, ctr_drbg_self_test_entropy, entropy_source_pr, nonce_pers_pr, 16, 32 ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
ctr_drbg_set_prediction_resistance( &ctx, CTR_DRBG_PR_ON );
if( ctr_drbg_random( &ctx, buf, CTR_DRBG_BLOCKSIZE ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( ctr_drbg_random( &ctx, buf, CTR_DRBG_BLOCKSIZE ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( memcmp( buf, result_pr, CTR_DRBG_BLOCKSIZE ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( verbose != 0 )
printf( "passed\n" );
/*
* Based on a NIST CTR_DRBG test vector (PR = FALSE)
*/
if( verbose != 0 )
printf( " CTR_DRBG (PR = FALSE): " );
test_offset = 0;
if( ctr_drbg_init_entropy_len( &ctx, ctr_drbg_self_test_entropy, entropy_source_nopr, nonce_pers_nopr, 16, 32 ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( ctr_drbg_random( &ctx, buf, 16 ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( ctr_drbg_reseed( &ctx, NULL, 0 ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( ctr_drbg_random( &ctx, buf, 16 ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( memcmp( buf, result_nopr, 16 ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( verbose != 0 )
printf( "passed\n" );
if( verbose != 0 )
printf( "\n" );
return( 0 );
}
#endif
#endif
-238
View File
@@ -1,238 +0,0 @@
/*
* Debugging routines
*
* Copyright (C) 2006-2010, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_DEBUG_C)
#include "polarssl/debug.h"
#include <stdarg.h>
#include <stdlib.h>
#if defined _MSC_VER && !defined snprintf
#define snprintf _snprintf
#endif
#if defined _MSC_VER && !defined vsnprintf
#define vsnprintf _vsnprintf
#endif
char *debug_fmt( const char *format, ... )
{
va_list argp;
static char str[512];
int maxlen = sizeof( str ) - 1;
va_start( argp, format );
vsnprintf( str, maxlen, format, argp );
va_end( argp );
str[maxlen] = '\0';
return( str );
}
void debug_print_msg( const ssl_context *ssl, int level,
const char *file, int line, const char *text )
{
char str[512];
int maxlen = sizeof( str ) - 1;
if( ssl->f_dbg == NULL )
return;
snprintf( str, maxlen, "%s(%04d): %s\n", file, line, text );
str[maxlen] = '\0';
ssl->f_dbg( ssl->p_dbg, level, str );
}
void debug_print_ret( const ssl_context *ssl, int level,
const char *file, int line,
const char *text, int ret )
{
char str[512];
int maxlen = sizeof( str ) - 1;
if( ssl->f_dbg == NULL )
return;
snprintf( str, maxlen, "%s(%04d): %s() returned %d (0x%x)\n",
file, line, text, ret, ret );
str[maxlen] = '\0';
ssl->f_dbg( ssl->p_dbg, level, str );
}
void debug_print_buf( const ssl_context *ssl, int level,
const char *file, int line, const char *text,
unsigned char *buf, size_t len )
{
char str[512];
size_t i, maxlen = sizeof( str ) - 1;
if( ssl->f_dbg == NULL )
return;
snprintf( str, maxlen, "%s(%04d): dumping '%s' (%d bytes)\n",
file, line, text, (unsigned int) len );
str[maxlen] = '\0';
ssl->f_dbg( ssl->p_dbg, level, str );
for( i = 0; i < len; i++ )
{
if( i >= 4096 )
break;
if( i % 16 == 0 )
{
if( i > 0 )
ssl->f_dbg( ssl->p_dbg, level, "\n" );
snprintf( str, maxlen, "%s(%04d): %04x: ", file, line,
(unsigned int) i );
str[maxlen] = '\0';
ssl->f_dbg( ssl->p_dbg, level, str );
}
snprintf( str, maxlen, " %02x", (unsigned int) buf[i] );
str[maxlen] = '\0';
ssl->f_dbg( ssl->p_dbg, level, str );
}
if( len > 0 )
ssl->f_dbg( ssl->p_dbg, level, "\n" );
}
void debug_print_mpi( const ssl_context *ssl, int level,
const char *file, int line,
const char *text, const mpi *X )
{
char str[512];
int j, k, maxlen = sizeof( str ) - 1, zeros = 1;
size_t i, n;
if( ssl->f_dbg == NULL || X == NULL )
return;
for( n = X->n - 1; n > 0; n-- )
if( X->p[n] != 0 )
break;
for( j = ( sizeof(t_uint) << 3 ) - 1; j >= 0; j-- )
if( ( ( X->p[n] >> j ) & 1 ) != 0 )
break;
snprintf( str, maxlen, "%s(%04d): value of '%s' (%d bits) is:\n",
file, line, text,
(int) ( ( n * ( sizeof(t_uint) << 3 ) ) + j + 1 ) );
str[maxlen] = '\0';
ssl->f_dbg( ssl->p_dbg, level, str );
for( i = n + 1, j = 0; i > 0; i-- )
{
if( zeros && X->p[i - 1] == 0 )
continue;
for( k = sizeof( t_uint ) - 1; k >= 0; k-- )
{
if( zeros && ( ( X->p[i - 1] >> (k << 3) ) & 0xFF ) == 0 )
continue;
else
zeros = 0;
if( j % 16 == 0 )
{
if( j > 0 )
ssl->f_dbg( ssl->p_dbg, level, "\n" );
snprintf( str, maxlen, "%s(%04d): ", file, line );
str[maxlen] = '\0';
ssl->f_dbg( ssl->p_dbg, level, str );
}
snprintf( str, maxlen, " %02x", (unsigned int)
( X->p[i - 1] >> (k << 3) ) & 0xFF );
str[maxlen] = '\0';
ssl->f_dbg( ssl->p_dbg, level, str );
j++;
}
}
if( zeros == 1 )
{
snprintf( str, maxlen, "%s(%04d): ", file, line );
str[maxlen] = '\0';
ssl->f_dbg( ssl->p_dbg, level, str );
ssl->f_dbg( ssl->p_dbg, level, " 00" );
}
ssl->f_dbg( ssl->p_dbg, level, "\n" );
}
void debug_print_crt( const ssl_context *ssl, int level,
const char *file, int line,
const char *text, const x509_cert *crt )
{
char str[1024], prefix[64];
int i = 0, maxlen = sizeof( prefix ) - 1;
if( ssl->f_dbg == NULL || crt == NULL )
return;
snprintf( prefix, maxlen, "%s(%04d): ", file, line );
prefix[maxlen] = '\0';
maxlen = sizeof( str ) - 1;
while( crt != NULL )
{
char buf[1024];
x509parse_cert_info( buf, sizeof( buf ) - 1, prefix, crt );
snprintf( str, maxlen, "%s(%04d): %s #%d:\n%s",
file, line, text, ++i, buf );
str[maxlen] = '\0';
ssl->f_dbg( ssl->p_dbg, level, str );
debug_print_mpi( ssl, level, file, line,
"crt->rsa.N", &crt->rsa.N );
debug_print_mpi( ssl, level, file, line,
"crt->rsa.E", &crt->rsa.E );
crt = crt->next;
}
}
#endif
-997
View File
@@ -1,997 +0,0 @@
/*
* FIPS-46-3 compliant Triple-DES implementation
*
* Copyright (C) 2006-2013, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*
* DES, on which TDES is based, was originally designed by Horst Feistel
* at IBM in 1974, and was adopted as a standard by NIST (formerly NBS).
*
* http://csrc.nist.gov/publications/fips/fips46-3/fips46-3.pdf
*/
#include "polarssl/config.h"
#if defined(POLARSSL_DES_C)
#include "polarssl/des.h"
#if !defined(POLARSSL_DES_ALT)
/*
* 32-bit integer manipulation macros (big endian)
*/
#ifndef GET_UINT32_BE
#define GET_UINT32_BE(n,b,i) \
{ \
(n) = ( (uint32_t) (b)[(i) ] << 24 ) \
| ( (uint32_t) (b)[(i) + 1] << 16 ) \
| ( (uint32_t) (b)[(i) + 2] << 8 ) \
| ( (uint32_t) (b)[(i) + 3] ); \
}
#endif
#ifndef PUT_UINT32_BE
#define PUT_UINT32_BE(n,b,i) \
{ \
(b)[(i) ] = (unsigned char) ( (n) >> 24 ); \
(b)[(i) + 1] = (unsigned char) ( (n) >> 16 ); \
(b)[(i) + 2] = (unsigned char) ( (n) >> 8 ); \
(b)[(i) + 3] = (unsigned char) ( (n) ); \
}
#endif
/*
* Expanded DES S-boxes
*/
static const uint32_t SB1[64] =
{
0x01010400, 0x00000000, 0x00010000, 0x01010404,
0x01010004, 0x00010404, 0x00000004, 0x00010000,
0x00000400, 0x01010400, 0x01010404, 0x00000400,
0x01000404, 0x01010004, 0x01000000, 0x00000004,
0x00000404, 0x01000400, 0x01000400, 0x00010400,
0x00010400, 0x01010000, 0x01010000, 0x01000404,
0x00010004, 0x01000004, 0x01000004, 0x00010004,
0x00000000, 0x00000404, 0x00010404, 0x01000000,
0x00010000, 0x01010404, 0x00000004, 0x01010000,
0x01010400, 0x01000000, 0x01000000, 0x00000400,
0x01010004, 0x00010000, 0x00010400, 0x01000004,
0x00000400, 0x00000004, 0x01000404, 0x00010404,
0x01010404, 0x00010004, 0x01010000, 0x01000404,
0x01000004, 0x00000404, 0x00010404, 0x01010400,
0x00000404, 0x01000400, 0x01000400, 0x00000000,
0x00010004, 0x00010400, 0x00000000, 0x01010004
};
static const uint32_t SB2[64] =
{
0x80108020, 0x80008000, 0x00008000, 0x00108020,
0x00100000, 0x00000020, 0x80100020, 0x80008020,
0x80000020, 0x80108020, 0x80108000, 0x80000000,
0x80008000, 0x00100000, 0x00000020, 0x80100020,
0x00108000, 0x00100020, 0x80008020, 0x00000000,
0x80000000, 0x00008000, 0x00108020, 0x80100000,
0x00100020, 0x80000020, 0x00000000, 0x00108000,
0x00008020, 0x80108000, 0x80100000, 0x00008020,
0x00000000, 0x00108020, 0x80100020, 0x00100000,
0x80008020, 0x80100000, 0x80108000, 0x00008000,
0x80100000, 0x80008000, 0x00000020, 0x80108020,
0x00108020, 0x00000020, 0x00008000, 0x80000000,
0x00008020, 0x80108000, 0x00100000, 0x80000020,
0x00100020, 0x80008020, 0x80000020, 0x00100020,
0x00108000, 0x00000000, 0x80008000, 0x00008020,
0x80000000, 0x80100020, 0x80108020, 0x00108000
};
static const uint32_t SB3[64] =
{
0x00000208, 0x08020200, 0x00000000, 0x08020008,
0x08000200, 0x00000000, 0x00020208, 0x08000200,
0x00020008, 0x08000008, 0x08000008, 0x00020000,
0x08020208, 0x00020008, 0x08020000, 0x00000208,
0x08000000, 0x00000008, 0x08020200, 0x00000200,
0x00020200, 0x08020000, 0x08020008, 0x00020208,
0x08000208, 0x00020200, 0x00020000, 0x08000208,
0x00000008, 0x08020208, 0x00000200, 0x08000000,
0x08020200, 0x08000000, 0x00020008, 0x00000208,
0x00020000, 0x08020200, 0x08000200, 0x00000000,
0x00000200, 0x00020008, 0x08020208, 0x08000200,
0x08000008, 0x00000200, 0x00000000, 0x08020008,
0x08000208, 0x00020000, 0x08000000, 0x08020208,
0x00000008, 0x00020208, 0x00020200, 0x08000008,
0x08020000, 0x08000208, 0x00000208, 0x08020000,
0x00020208, 0x00000008, 0x08020008, 0x00020200
};
static const uint32_t SB4[64] =
{
0x00802001, 0x00002081, 0x00002081, 0x00000080,
0x00802080, 0x00800081, 0x00800001, 0x00002001,
0x00000000, 0x00802000, 0x00802000, 0x00802081,
0x00000081, 0x00000000, 0x00800080, 0x00800001,
0x00000001, 0x00002000, 0x00800000, 0x00802001,
0x00000080, 0x00800000, 0x00002001, 0x00002080,
0x00800081, 0x00000001, 0x00002080, 0x00800080,
0x00002000, 0x00802080, 0x00802081, 0x00000081,
0x00800080, 0x00800001, 0x00802000, 0x00802081,
0x00000081, 0x00000000, 0x00000000, 0x00802000,
0x00002080, 0x00800080, 0x00800081, 0x00000001,
0x00802001, 0x00002081, 0x00002081, 0x00000080,
0x00802081, 0x00000081, 0x00000001, 0x00002000,
0x00800001, 0x00002001, 0x00802080, 0x00800081,
0x00002001, 0x00002080, 0x00800000, 0x00802001,
0x00000080, 0x00800000, 0x00002000, 0x00802080
};
static const uint32_t SB5[64] =
{
0x00000100, 0x02080100, 0x02080000, 0x42000100,
0x00080000, 0x00000100, 0x40000000, 0x02080000,
0x40080100, 0x00080000, 0x02000100, 0x40080100,
0x42000100, 0x42080000, 0x00080100, 0x40000000,
0x02000000, 0x40080000, 0x40080000, 0x00000000,
0x40000100, 0x42080100, 0x42080100, 0x02000100,
0x42080000, 0x40000100, 0x00000000, 0x42000000,
0x02080100, 0x02000000, 0x42000000, 0x00080100,
0x00080000, 0x42000100, 0x00000100, 0x02000000,
0x40000000, 0x02080000, 0x42000100, 0x40080100,
0x02000100, 0x40000000, 0x42080000, 0x02080100,
0x40080100, 0x00000100, 0x02000000, 0x42080000,
0x42080100, 0x00080100, 0x42000000, 0x42080100,
0x02080000, 0x00000000, 0x40080000, 0x42000000,
0x00080100, 0x02000100, 0x40000100, 0x00080000,
0x00000000, 0x40080000, 0x02080100, 0x40000100
};
static const uint32_t SB6[64] =
{
0x20000010, 0x20400000, 0x00004000, 0x20404010,
0x20400000, 0x00000010, 0x20404010, 0x00400000,
0x20004000, 0x00404010, 0x00400000, 0x20000010,
0x00400010, 0x20004000, 0x20000000, 0x00004010,
0x00000000, 0x00400010, 0x20004010, 0x00004000,
0x00404000, 0x20004010, 0x00000010, 0x20400010,
0x20400010, 0x00000000, 0x00404010, 0x20404000,
0x00004010, 0x00404000, 0x20404000, 0x20000000,
0x20004000, 0x00000010, 0x20400010, 0x00404000,
0x20404010, 0x00400000, 0x00004010, 0x20000010,
0x00400000, 0x20004000, 0x20000000, 0x00004010,
0x20000010, 0x20404010, 0x00404000, 0x20400000,
0x00404010, 0x20404000, 0x00000000, 0x20400010,
0x00000010, 0x00004000, 0x20400000, 0x00404010,
0x00004000, 0x00400010, 0x20004010, 0x00000000,
0x20404000, 0x20000000, 0x00400010, 0x20004010
};
static const uint32_t SB7[64] =
{
0x00200000, 0x04200002, 0x04000802, 0x00000000,
0x00000800, 0x04000802, 0x00200802, 0x04200800,
0x04200802, 0x00200000, 0x00000000, 0x04000002,
0x00000002, 0x04000000, 0x04200002, 0x00000802,
0x04000800, 0x00200802, 0x00200002, 0x04000800,
0x04000002, 0x04200000, 0x04200800, 0x00200002,
0x04200000, 0x00000800, 0x00000802, 0x04200802,
0x00200800, 0x00000002, 0x04000000, 0x00200800,
0x04000000, 0x00200800, 0x00200000, 0x04000802,
0x04000802, 0x04200002, 0x04200002, 0x00000002,
0x00200002, 0x04000000, 0x04000800, 0x00200000,
0x04200800, 0x00000802, 0x00200802, 0x04200800,
0x00000802, 0x04000002, 0x04200802, 0x04200000,
0x00200800, 0x00000000, 0x00000002, 0x04200802,
0x00000000, 0x00200802, 0x04200000, 0x00000800,
0x04000002, 0x04000800, 0x00000800, 0x00200002
};
static const uint32_t SB8[64] =
{
0x10001040, 0x00001000, 0x00040000, 0x10041040,
0x10000000, 0x10001040, 0x00000040, 0x10000000,
0x00040040, 0x10040000, 0x10041040, 0x00041000,
0x10041000, 0x00041040, 0x00001000, 0x00000040,
0x10040000, 0x10000040, 0x10001000, 0x00001040,
0x00041000, 0x00040040, 0x10040040, 0x10041000,
0x00001040, 0x00000000, 0x00000000, 0x10040040,
0x10000040, 0x10001000, 0x00041040, 0x00040000,
0x00041040, 0x00040000, 0x10041000, 0x00001000,
0x00000040, 0x10040040, 0x00001000, 0x00041040,
0x10001000, 0x00000040, 0x10000040, 0x10040000,
0x10040040, 0x10000000, 0x00040000, 0x10001040,
0x00000000, 0x10041040, 0x00040040, 0x10000040,
0x10040000, 0x10001000, 0x10001040, 0x00000000,
0x10041040, 0x00041000, 0x00041000, 0x00001040,
0x00001040, 0x00040040, 0x10000000, 0x10041000
};
/*
* PC1: left and right halves bit-swap
*/
static const uint32_t LHs[16] =
{
0x00000000, 0x00000001, 0x00000100, 0x00000101,
0x00010000, 0x00010001, 0x00010100, 0x00010101,
0x01000000, 0x01000001, 0x01000100, 0x01000101,
0x01010000, 0x01010001, 0x01010100, 0x01010101
};
static const uint32_t RHs[16] =
{
0x00000000, 0x01000000, 0x00010000, 0x01010000,
0x00000100, 0x01000100, 0x00010100, 0x01010100,
0x00000001, 0x01000001, 0x00010001, 0x01010001,
0x00000101, 0x01000101, 0x00010101, 0x01010101,
};
/*
* Initial Permutation macro
*/
#define DES_IP(X,Y) \
{ \
T = ((X >> 4) ^ Y) & 0x0F0F0F0F; Y ^= T; X ^= (T << 4); \
T = ((X >> 16) ^ Y) & 0x0000FFFF; Y ^= T; X ^= (T << 16); \
T = ((Y >> 2) ^ X) & 0x33333333; X ^= T; Y ^= (T << 2); \
T = ((Y >> 8) ^ X) & 0x00FF00FF; X ^= T; Y ^= (T << 8); \
Y = ((Y << 1) | (Y >> 31)) & 0xFFFFFFFF; \
T = (X ^ Y) & 0xAAAAAAAA; Y ^= T; X ^= T; \
X = ((X << 1) | (X >> 31)) & 0xFFFFFFFF; \
}
/*
* Final Permutation macro
*/
#define DES_FP(X,Y) \
{ \
X = ((X << 31) | (X >> 1)) & 0xFFFFFFFF; \
T = (X ^ Y) & 0xAAAAAAAA; X ^= T; Y ^= T; \
Y = ((Y << 31) | (Y >> 1)) & 0xFFFFFFFF; \
T = ((Y >> 8) ^ X) & 0x00FF00FF; X ^= T; Y ^= (T << 8); \
T = ((Y >> 2) ^ X) & 0x33333333; X ^= T; Y ^= (T << 2); \
T = ((X >> 16) ^ Y) & 0x0000FFFF; Y ^= T; X ^= (T << 16); \
T = ((X >> 4) ^ Y) & 0x0F0F0F0F; Y ^= T; X ^= (T << 4); \
}
/*
* DES round macro
*/
#define DES_ROUND(X,Y) \
{ \
T = *SK++ ^ X; \
Y ^= SB8[ (T ) & 0x3F ] ^ \
SB6[ (T >> 8) & 0x3F ] ^ \
SB4[ (T >> 16) & 0x3F ] ^ \
SB2[ (T >> 24) & 0x3F ]; \
\
T = *SK++ ^ ((X << 28) | (X >> 4)); \
Y ^= SB7[ (T ) & 0x3F ] ^ \
SB5[ (T >> 8) & 0x3F ] ^ \
SB3[ (T >> 16) & 0x3F ] ^ \
SB1[ (T >> 24) & 0x3F ]; \
}
#define SWAP(a,b) { uint32_t t = a; a = b; b = t; t = 0; }
static const unsigned char odd_parity_table[128] = { 1, 2, 4, 7, 8,
11, 13, 14, 16, 19, 21, 22, 25, 26, 28, 31, 32, 35, 37, 38, 41, 42, 44,
47, 49, 50, 52, 55, 56, 59, 61, 62, 64, 67, 69, 70, 73, 74, 76, 79, 81,
82, 84, 87, 88, 91, 93, 94, 97, 98, 100, 103, 104, 107, 109, 110, 112,
115, 117, 118, 121, 122, 124, 127, 128, 131, 133, 134, 137, 138, 140,
143, 145, 146, 148, 151, 152, 155, 157, 158, 161, 162, 164, 167, 168,
171, 173, 174, 176, 179, 181, 182, 185, 186, 188, 191, 193, 194, 196,
199, 200, 203, 205, 206, 208, 211, 213, 214, 217, 218, 220, 223, 224,
227, 229, 230, 233, 234, 236, 239, 241, 242, 244, 247, 248, 251, 253,
254 };
void des_key_set_parity( unsigned char key[DES_KEY_SIZE] )
{
int i;
for( i = 0; i < DES_KEY_SIZE; i++ )
key[i] = odd_parity_table[key[i] / 2];
}
/*
* Check the given key's parity, returns 1 on failure, 0 on SUCCESS
*/
int des_key_check_key_parity( const unsigned char key[DES_KEY_SIZE] )
{
int i;
for( i = 0; i < DES_KEY_SIZE; i++ )
if ( key[i] != odd_parity_table[key[i] / 2] )
return( 1 );
return( 0 );
}
/*
* Table of weak and semi-weak keys
*
* Source: http://en.wikipedia.org/wiki/Weak_key
*
* Weak:
* Alternating ones + zeros (0x0101010101010101)
* Alternating 'F' + 'E' (0xFEFEFEFEFEFEFEFE)
* '0xE0E0E0E0F1F1F1F1'
* '0x1F1F1F1F0E0E0E0E'
*
* Semi-weak:
* 0x011F011F010E010E and 0x1F011F010E010E01
* 0x01E001E001F101F1 and 0xE001E001F101F101
* 0x01FE01FE01FE01FE and 0xFE01FE01FE01FE01
* 0x1FE01FE00EF10EF1 and 0xE01FE01FF10EF10E
* 0x1FFE1FFE0EFE0EFE and 0xFE1FFE1FFE0EFE0E
* 0xE0FEE0FEF1FEF1FE and 0xFEE0FEE0FEF1FEF1
*
*/
#define WEAK_KEY_COUNT 16
static const unsigned char weak_key_table[WEAK_KEY_COUNT][DES_KEY_SIZE] =
{
{ 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01 },
{ 0xFE, 0xFE, 0xFE, 0xFE, 0xFE, 0xFE, 0xFE, 0xFE },
{ 0x1F, 0x1F, 0x1F, 0x1F, 0x0E, 0x0E, 0x0E, 0x0E },
{ 0xE0, 0xE0, 0xE0, 0xE0, 0xF1, 0xF1, 0xF1, 0xF1 },
{ 0x01, 0x1F, 0x01, 0x1F, 0x01, 0x0E, 0x01, 0x0E },
{ 0x1F, 0x01, 0x1F, 0x01, 0x0E, 0x01, 0x0E, 0x01 },
{ 0x01, 0xE0, 0x01, 0xE0, 0x01, 0xF1, 0x01, 0xF1 },
{ 0xE0, 0x01, 0xE0, 0x01, 0xF1, 0x01, 0xF1, 0x01 },
{ 0x01, 0xFE, 0x01, 0xFE, 0x01, 0xFE, 0x01, 0xFE },
{ 0xFE, 0x01, 0xFE, 0x01, 0xFE, 0x01, 0xFE, 0x01 },
{ 0x1F, 0xE0, 0x1F, 0xE0, 0x0E, 0xF1, 0x0E, 0xF1 },
{ 0xE0, 0x1F, 0xE0, 0x1F, 0xF1, 0x0E, 0xF1, 0x0E },
{ 0x1F, 0xFE, 0x1F, 0xFE, 0x0E, 0xFE, 0x0E, 0xFE },
{ 0xFE, 0x1F, 0xFE, 0x1F, 0xFE, 0x0E, 0xFE, 0x0E },
{ 0xE0, 0xFE, 0xE0, 0xFE, 0xF1, 0xFE, 0xF1, 0xFE },
{ 0xFE, 0xE0, 0xFE, 0xE0, 0xFE, 0xF1, 0xFE, 0xF1 }
};
int des_key_check_weak( const unsigned char key[DES_KEY_SIZE] )
{
int i;
for( i = 0; i < WEAK_KEY_COUNT; i++ )
if( memcmp( weak_key_table[i], key, DES_KEY_SIZE) == 0)
return( 1 );
return( 0 );
}
static void des_setkey( uint32_t SK[32], const unsigned char key[DES_KEY_SIZE] )
{
int i;
uint32_t X, Y, T;
GET_UINT32_BE( X, key, 0 );
GET_UINT32_BE( Y, key, 4 );
/*
* Permuted Choice 1
*/
T = ((Y >> 4) ^ X) & 0x0F0F0F0F; X ^= T; Y ^= (T << 4);
T = ((Y ) ^ X) & 0x10101010; X ^= T; Y ^= (T );
X = (LHs[ (X ) & 0xF] << 3) | (LHs[ (X >> 8) & 0xF ] << 2)
| (LHs[ (X >> 16) & 0xF] << 1) | (LHs[ (X >> 24) & 0xF ] )
| (LHs[ (X >> 5) & 0xF] << 7) | (LHs[ (X >> 13) & 0xF ] << 6)
| (LHs[ (X >> 21) & 0xF] << 5) | (LHs[ (X >> 29) & 0xF ] << 4);
Y = (RHs[ (Y >> 1) & 0xF] << 3) | (RHs[ (Y >> 9) & 0xF ] << 2)
| (RHs[ (Y >> 17) & 0xF] << 1) | (RHs[ (Y >> 25) & 0xF ] )
| (RHs[ (Y >> 4) & 0xF] << 7) | (RHs[ (Y >> 12) & 0xF ] << 6)
| (RHs[ (Y >> 20) & 0xF] << 5) | (RHs[ (Y >> 28) & 0xF ] << 4);
X &= 0x0FFFFFFF;
Y &= 0x0FFFFFFF;
/*
* calculate subkeys
*/
for( i = 0; i < 16; i++ )
{
if( i < 2 || i == 8 || i == 15 )
{
X = ((X << 1) | (X >> 27)) & 0x0FFFFFFF;
Y = ((Y << 1) | (Y >> 27)) & 0x0FFFFFFF;
}
else
{
X = ((X << 2) | (X >> 26)) & 0x0FFFFFFF;
Y = ((Y << 2) | (Y >> 26)) & 0x0FFFFFFF;
}
*SK++ = ((X << 4) & 0x24000000) | ((X << 28) & 0x10000000)
| ((X << 14) & 0x08000000) | ((X << 18) & 0x02080000)
| ((X << 6) & 0x01000000) | ((X << 9) & 0x00200000)
| ((X >> 1) & 0x00100000) | ((X << 10) & 0x00040000)
| ((X << 2) & 0x00020000) | ((X >> 10) & 0x00010000)
| ((Y >> 13) & 0x00002000) | ((Y >> 4) & 0x00001000)
| ((Y << 6) & 0x00000800) | ((Y >> 1) & 0x00000400)
| ((Y >> 14) & 0x00000200) | ((Y ) & 0x00000100)
| ((Y >> 5) & 0x00000020) | ((Y >> 10) & 0x00000010)
| ((Y >> 3) & 0x00000008) | ((Y >> 18) & 0x00000004)
| ((Y >> 26) & 0x00000002) | ((Y >> 24) & 0x00000001);
*SK++ = ((X << 15) & 0x20000000) | ((X << 17) & 0x10000000)
| ((X << 10) & 0x08000000) | ((X << 22) & 0x04000000)
| ((X >> 2) & 0x02000000) | ((X << 1) & 0x01000000)
| ((X << 16) & 0x00200000) | ((X << 11) & 0x00100000)
| ((X << 3) & 0x00080000) | ((X >> 6) & 0x00040000)
| ((X << 15) & 0x00020000) | ((X >> 4) & 0x00010000)
| ((Y >> 2) & 0x00002000) | ((Y << 8) & 0x00001000)
| ((Y >> 14) & 0x00000808) | ((Y >> 9) & 0x00000400)
| ((Y ) & 0x00000200) | ((Y << 7) & 0x00000100)
| ((Y >> 7) & 0x00000020) | ((Y >> 3) & 0x00000011)
| ((Y << 2) & 0x00000004) | ((Y >> 21) & 0x00000002);
}
}
/*
* DES key schedule (56-bit, encryption)
*/
int des_setkey_enc( des_context *ctx, const unsigned char key[DES_KEY_SIZE] )
{
des_setkey( ctx->sk, key );
return( 0 );
}
/*
* DES key schedule (56-bit, decryption)
*/
int des_setkey_dec( des_context *ctx, const unsigned char key[DES_KEY_SIZE] )
{
int i;
des_setkey( ctx->sk, key );
for( i = 0; i < 16; i += 2 )
{
SWAP( ctx->sk[i ], ctx->sk[30 - i] );
SWAP( ctx->sk[i + 1], ctx->sk[31 - i] );
}
return( 0 );
}
static void des3_set2key( uint32_t esk[96],
uint32_t dsk[96],
const unsigned char key[DES_KEY_SIZE*2] )
{
int i;
des_setkey( esk, key );
des_setkey( dsk + 32, key + 8 );
for( i = 0; i < 32; i += 2 )
{
dsk[i ] = esk[30 - i];
dsk[i + 1] = esk[31 - i];
esk[i + 32] = dsk[62 - i];
esk[i + 33] = dsk[63 - i];
esk[i + 64] = esk[i ];
esk[i + 65] = esk[i + 1];
dsk[i + 64] = dsk[i ];
dsk[i + 65] = dsk[i + 1];
}
}
/*
* Triple-DES key schedule (112-bit, encryption)
*/
int des3_set2key_enc( des3_context *ctx, const unsigned char key[DES_KEY_SIZE * 2] )
{
uint32_t sk[96];
des3_set2key( ctx->sk, sk, key );
memset( sk, 0, sizeof( sk ) );
return( 0 );
}
/*
* Triple-DES key schedule (112-bit, decryption)
*/
int des3_set2key_dec( des3_context *ctx, const unsigned char key[DES_KEY_SIZE * 2] )
{
uint32_t sk[96];
des3_set2key( sk, ctx->sk, key );
memset( sk, 0, sizeof( sk ) );
return( 0 );
}
static void des3_set3key( uint32_t esk[96],
uint32_t dsk[96],
const unsigned char key[24] )
{
int i;
des_setkey( esk, key );
des_setkey( dsk + 32, key + 8 );
des_setkey( esk + 64, key + 16 );
for( i = 0; i < 32; i += 2 )
{
dsk[i ] = esk[94 - i];
dsk[i + 1] = esk[95 - i];
esk[i + 32] = dsk[62 - i];
esk[i + 33] = dsk[63 - i];
dsk[i + 64] = esk[30 - i];
dsk[i + 65] = esk[31 - i];
}
}
/*
* Triple-DES key schedule (168-bit, encryption)
*/
int des3_set3key_enc( des3_context *ctx, const unsigned char key[DES_KEY_SIZE * 3] )
{
uint32_t sk[96];
des3_set3key( ctx->sk, sk, key );
memset( sk, 0, sizeof( sk ) );
return( 0 );
}
/*
* Triple-DES key schedule (168-bit, decryption)
*/
int des3_set3key_dec( des3_context *ctx, const unsigned char key[DES_KEY_SIZE * 3] )
{
uint32_t sk[96];
des3_set3key( sk, ctx->sk, key );
memset( sk, 0, sizeof( sk ) );
return( 0 );
}
/*
* DES-ECB block encryption/decryption
*/
int des_crypt_ecb( des_context *ctx,
const unsigned char input[8],
unsigned char output[8] )
{
int i;
uint32_t X, Y, T, *SK;
SK = ctx->sk;
GET_UINT32_BE( X, input, 0 );
GET_UINT32_BE( Y, input, 4 );
DES_IP( X, Y );
for( i = 0; i < 8; i++ )
{
DES_ROUND( Y, X );
DES_ROUND( X, Y );
}
DES_FP( Y, X );
PUT_UINT32_BE( Y, output, 0 );
PUT_UINT32_BE( X, output, 4 );
return( 0 );
}
/*
* DES-CBC buffer encryption/decryption
*/
int des_crypt_cbc( des_context *ctx,
int mode,
size_t length,
unsigned char iv[8],
const unsigned char *input,
unsigned char *output )
{
int i;
unsigned char temp[8];
if( length % 8 )
return( POLARSSL_ERR_DES_INVALID_INPUT_LENGTH );
if( mode == DES_ENCRYPT )
{
while( length > 0 )
{
for( i = 0; i < 8; i++ )
output[i] = (unsigned char)( input[i] ^ iv[i] );
des_crypt_ecb( ctx, output, output );
memcpy( iv, output, 8 );
input += 8;
output += 8;
length -= 8;
}
}
else /* DES_DECRYPT */
{
while( length > 0 )
{
memcpy( temp, input, 8 );
des_crypt_ecb( ctx, input, output );
for( i = 0; i < 8; i++ )
output[i] = (unsigned char)( output[i] ^ iv[i] );
memcpy( iv, temp, 8 );
input += 8;
output += 8;
length -= 8;
}
}
return( 0 );
}
/*
* 3DES-ECB block encryption/decryption
*/
int des3_crypt_ecb( des3_context *ctx,
const unsigned char input[8],
unsigned char output[8] )
{
int i;
uint32_t X, Y, T, *SK;
SK = ctx->sk;
GET_UINT32_BE( X, input, 0 );
GET_UINT32_BE( Y, input, 4 );
DES_IP( X, Y );
for( i = 0; i < 8; i++ )
{
DES_ROUND( Y, X );
DES_ROUND( X, Y );
}
for( i = 0; i < 8; i++ )
{
DES_ROUND( X, Y );
DES_ROUND( Y, X );
}
for( i = 0; i < 8; i++ )
{
DES_ROUND( Y, X );
DES_ROUND( X, Y );
}
DES_FP( Y, X );
PUT_UINT32_BE( Y, output, 0 );
PUT_UINT32_BE( X, output, 4 );
return( 0 );
}
/*
* 3DES-CBC buffer encryption/decryption
*/
int des3_crypt_cbc( des3_context *ctx,
int mode,
size_t length,
unsigned char iv[8],
const unsigned char *input,
unsigned char *output )
{
int i;
unsigned char temp[8];
if( length % 8 )
return( POLARSSL_ERR_DES_INVALID_INPUT_LENGTH );
if( mode == DES_ENCRYPT )
{
while( length > 0 )
{
for( i = 0; i < 8; i++ )
output[i] = (unsigned char)( input[i] ^ iv[i] );
des3_crypt_ecb( ctx, output, output );
memcpy( iv, output, 8 );
input += 8;
output += 8;
length -= 8;
}
}
else /* DES_DECRYPT */
{
while( length > 0 )
{
memcpy( temp, input, 8 );
des3_crypt_ecb( ctx, input, output );
for( i = 0; i < 8; i++ )
output[i] = (unsigned char)( output[i] ^ iv[i] );
memcpy( iv, temp, 8 );
input += 8;
output += 8;
length -= 8;
}
}
return( 0 );
}
#endif /* !POLARSSL_DES_ALT */
#if defined(POLARSSL_SELF_TEST)
#include <stdio.h>
/*
* DES and 3DES test vectors from:
*
* http://csrc.nist.gov/groups/STM/cavp/documents/des/tripledes-vectors.zip
*/
static const unsigned char des3_test_keys[24] =
{
0x01, 0x23, 0x45, 0x67, 0x89, 0xAB, 0xCD, 0xEF,
0x23, 0x45, 0x67, 0x89, 0xAB, 0xCD, 0xEF, 0x01,
0x45, 0x67, 0x89, 0xAB, 0xCD, 0xEF, 0x01, 0x23
};
static const unsigned char des3_test_iv[8] =
{
0x12, 0x34, 0x56, 0x78, 0x90, 0xAB, 0xCD, 0xEF,
};
static const unsigned char des3_test_buf[8] =
{
0x4E, 0x6F, 0x77, 0x20, 0x69, 0x73, 0x20, 0x74
};
static const unsigned char des3_test_ecb_dec[3][8] =
{
{ 0xCD, 0xD6, 0x4F, 0x2F, 0x94, 0x27, 0xC1, 0x5D },
{ 0x69, 0x96, 0xC8, 0xFA, 0x47, 0xA2, 0xAB, 0xEB },
{ 0x83, 0x25, 0x39, 0x76, 0x44, 0x09, 0x1A, 0x0A }
};
static const unsigned char des3_test_ecb_enc[3][8] =
{
{ 0x6A, 0x2A, 0x19, 0xF4, 0x1E, 0xCA, 0x85, 0x4B },
{ 0x03, 0xE6, 0x9F, 0x5B, 0xFA, 0x58, 0xEB, 0x42 },
{ 0xDD, 0x17, 0xE8, 0xB8, 0xB4, 0x37, 0xD2, 0x32 }
};
static const unsigned char des3_test_cbc_dec[3][8] =
{
{ 0x12, 0x9F, 0x40, 0xB9, 0xD2, 0x00, 0x56, 0xB3 },
{ 0x47, 0x0E, 0xFC, 0x9A, 0x6B, 0x8E, 0xE3, 0x93 },
{ 0xC5, 0xCE, 0xCF, 0x63, 0xEC, 0xEC, 0x51, 0x4C }
};
static const unsigned char des3_test_cbc_enc[3][8] =
{
{ 0x54, 0xF1, 0x5A, 0xF6, 0xEB, 0xE3, 0xA4, 0xB4 },
{ 0x35, 0x76, 0x11, 0x56, 0x5F, 0xA1, 0x8E, 0x4D },
{ 0xCB, 0x19, 0x1F, 0x85, 0xD1, 0xED, 0x84, 0x39 }
};
/*
* Checkup routine
*/
int des_self_test( int verbose )
{
int i, j, u, v;
des_context ctx;
des3_context ctx3;
unsigned char key[24];
unsigned char buf[8];
unsigned char prv[8];
unsigned char iv[8];
memset( key, 0, 24 );
/*
* ECB mode
*/
for( i = 0; i < 6; i++ )
{
u = i >> 1;
v = i & 1;
if( verbose != 0 )
printf( " DES%c-ECB-%3d (%s): ",
( u == 0 ) ? ' ' : '3', 56 + u * 56,
( v == DES_DECRYPT ) ? "dec" : "enc" );
memcpy( buf, des3_test_buf, 8 );
switch( i )
{
case 0:
des_setkey_dec( &ctx, des3_test_keys );
break;
case 1:
des_setkey_enc( &ctx, des3_test_keys );
break;
case 2:
des3_set2key_dec( &ctx3, des3_test_keys );
break;
case 3:
des3_set2key_enc( &ctx3, des3_test_keys );
break;
case 4:
des3_set3key_dec( &ctx3, des3_test_keys );
break;
case 5:
des3_set3key_enc( &ctx3, des3_test_keys );
break;
default:
return( 1 );
}
for( j = 0; j < 10000; j++ )
{
if( u == 0 )
des_crypt_ecb( &ctx, buf, buf );
else
des3_crypt_ecb( &ctx3, buf, buf );
}
if( ( v == DES_DECRYPT &&
memcmp( buf, des3_test_ecb_dec[u], 8 ) != 0 ) ||
( v != DES_DECRYPT &&
memcmp( buf, des3_test_ecb_enc[u], 8 ) != 0 ) )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( verbose != 0 )
printf( "passed\n" );
}
if( verbose != 0 )
printf( "\n" );
/*
* CBC mode
*/
for( i = 0; i < 6; i++ )
{
u = i >> 1;
v = i & 1;
if( verbose != 0 )
printf( " DES%c-CBC-%3d (%s): ",
( u == 0 ) ? ' ' : '3', 56 + u * 56,
( v == DES_DECRYPT ) ? "dec" : "enc" );
memcpy( iv, des3_test_iv, 8 );
memcpy( prv, des3_test_iv, 8 );
memcpy( buf, des3_test_buf, 8 );
switch( i )
{
case 0:
des_setkey_dec( &ctx, des3_test_keys );
break;
case 1:
des_setkey_enc( &ctx, des3_test_keys );
break;
case 2:
des3_set2key_dec( &ctx3, des3_test_keys );
break;
case 3:
des3_set2key_enc( &ctx3, des3_test_keys );
break;
case 4:
des3_set3key_dec( &ctx3, des3_test_keys );
break;
case 5:
des3_set3key_enc( &ctx3, des3_test_keys );
break;
default:
return( 1 );
}
if( v == DES_DECRYPT )
{
for( j = 0; j < 10000; j++ )
{
if( u == 0 )
des_crypt_cbc( &ctx, v, 8, iv, buf, buf );
else
des3_crypt_cbc( &ctx3, v, 8, iv, buf, buf );
}
}
else
{
for( j = 0; j < 10000; j++ )
{
unsigned char tmp[8];
if( u == 0 )
des_crypt_cbc( &ctx, v, 8, iv, buf, buf );
else
des3_crypt_cbc( &ctx3, v, 8, iv, buf, buf );
memcpy( tmp, prv, 8 );
memcpy( prv, buf, 8 );
memcpy( buf, tmp, 8 );
}
memcpy( buf, prv, 8 );
}
if( ( v == DES_DECRYPT &&
memcmp( buf, des3_test_cbc_dec[u], 8 ) != 0 ) ||
( v != DES_DECRYPT &&
memcmp( buf, des3_test_cbc_enc[u], 8 ) != 0 ) )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( verbose != 0 )
printf( "passed\n" );
}
if( verbose != 0 )
printf( "\n" );
return( 0 );
}
#endif
#endif
-302
View File
@@ -1,302 +0,0 @@
/*
* Diffie-Hellman-Merkle key exchange
*
* Copyright (C) 2006-2010, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*
* Reference:
*
* http://www.cacr.math.uwaterloo.ca/hac/ (chapter 12)
*/
#include "polarssl/config.h"
#if defined(POLARSSL_DHM_C)
#include "polarssl/dhm.h"
/*
* helper to validate the mpi size and import it
*/
static int dhm_read_bignum( mpi *X,
unsigned char **p,
const unsigned char *end )
{
int ret, n;
if( end - *p < 2 )
return( POLARSSL_ERR_DHM_BAD_INPUT_DATA );
n = ( (*p)[0] << 8 ) | (*p)[1];
(*p) += 2;
if( (int)( end - *p ) < n )
return( POLARSSL_ERR_DHM_BAD_INPUT_DATA );
if( ( ret = mpi_read_binary( X, *p, n ) ) != 0 )
return( POLARSSL_ERR_DHM_READ_PARAMS_FAILED + ret );
(*p) += n;
return( 0 );
}
/*
* Verify sanity of parameter with regards to P
*
* Parameter should be: 2 <= public_param <= P - 2
*
* For more information on the attack, see:
* http://www.cl.cam.ac.uk/~rja14/Papers/psandqs.pdf
* http://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2005-2643
*/
static int dhm_check_range( const mpi *param, const mpi *P )
{
mpi L, U;
int ret = POLARSSL_ERR_DHM_BAD_INPUT_DATA;
mpi_init( &L ); mpi_init( &U );
mpi_lset( &L, 2 );
mpi_sub_int( &U, P, 2 );
if( mpi_cmp_mpi( param, &L ) >= 0 &&
mpi_cmp_mpi( param, &U ) <= 0 )
{
ret = 0;
}
mpi_free( &L ); mpi_free( &U );
return( ret );
}
/*
* Parse the ServerKeyExchange parameters
*/
int dhm_read_params( dhm_context *ctx,
unsigned char **p,
const unsigned char *end )
{
int ret;
memset( ctx, 0, sizeof( dhm_context ) );
if( ( ret = dhm_read_bignum( &ctx->P, p, end ) ) != 0 ||
( ret = dhm_read_bignum( &ctx->G, p, end ) ) != 0 ||
( ret = dhm_read_bignum( &ctx->GY, p, end ) ) != 0 )
return( ret );
if( ( ret = dhm_check_range( &ctx->GY, &ctx->P ) ) != 0 )
return( ret );
ctx->len = mpi_size( &ctx->P );
if( end - *p < 2 )
return( POLARSSL_ERR_DHM_BAD_INPUT_DATA );
return( 0 );
}
/*
* Setup and write the ServerKeyExchange parameters
*/
int dhm_make_params( dhm_context *ctx, int x_size,
unsigned char *output, size_t *olen,
int (*f_rng)(void *, unsigned char *, size_t),
void *p_rng )
{
int ret, count = 0;
size_t n1, n2, n3;
unsigned char *p;
if( mpi_cmp_int( &ctx->P, 0 ) == 0 )
return( POLARSSL_ERR_DHM_BAD_INPUT_DATA );
/*
* Generate X as large as possible ( < P )
*/
do
{
mpi_fill_random( &ctx->X, x_size, f_rng, p_rng );
while( mpi_cmp_mpi( &ctx->X, &ctx->P ) >= 0 )
mpi_shift_r( &ctx->X, 1 );
if( count++ > 10 )
return( POLARSSL_ERR_DHM_MAKE_PARAMS_FAILED );
}
while( dhm_check_range( &ctx->X, &ctx->P ) != 0 );
/*
* Calculate GX = G^X mod P
*/
MPI_CHK( mpi_exp_mod( &ctx->GX, &ctx->G, &ctx->X,
&ctx->P , &ctx->RP ) );
if( ( ret = dhm_check_range( &ctx->GX, &ctx->P ) ) != 0 )
return( ret );
/*
* export P, G, GX
*/
#define DHM_MPI_EXPORT(X,n) \
MPI_CHK( mpi_write_binary( X, p + 2, n ) ); \
*p++ = (unsigned char)( n >> 8 ); \
*p++ = (unsigned char)( n ); p += n;
n1 = mpi_size( &ctx->P );
n2 = mpi_size( &ctx->G );
n3 = mpi_size( &ctx->GX );
p = output;
DHM_MPI_EXPORT( &ctx->P , n1 );
DHM_MPI_EXPORT( &ctx->G , n2 );
DHM_MPI_EXPORT( &ctx->GX, n3 );
*olen = p - output;
ctx->len = n1;
cleanup:
if( ret != 0 )
return( POLARSSL_ERR_DHM_MAKE_PARAMS_FAILED + ret );
return( 0 );
}
/*
* Import the peer's public value G^Y
*/
int dhm_read_public( dhm_context *ctx,
const unsigned char *input, size_t ilen )
{
int ret;
if( ctx == NULL || ilen < 1 || ilen > ctx->len )
return( POLARSSL_ERR_DHM_BAD_INPUT_DATA );
if( ( ret = mpi_read_binary( &ctx->GY, input, ilen ) ) != 0 )
return( POLARSSL_ERR_DHM_READ_PUBLIC_FAILED + ret );
return( 0 );
}
/*
* Create own private value X and export G^X
*/
int dhm_make_public( dhm_context *ctx, int x_size,
unsigned char *output, size_t olen,
int (*f_rng)(void *, unsigned char *, size_t),
void *p_rng )
{
int ret, count = 0;
if( ctx == NULL || olen < 1 || olen > ctx->len )
return( POLARSSL_ERR_DHM_BAD_INPUT_DATA );
if( mpi_cmp_int( &ctx->P, 0 ) == 0 )
return( POLARSSL_ERR_DHM_BAD_INPUT_DATA );
/*
* generate X and calculate GX = G^X mod P
*/
do
{
mpi_fill_random( &ctx->X, x_size, f_rng, p_rng );
while( mpi_cmp_mpi( &ctx->X, &ctx->P ) >= 0 )
mpi_shift_r( &ctx->X, 1 );
if( count++ > 10 )
return( POLARSSL_ERR_DHM_MAKE_PUBLIC_FAILED );
}
while( dhm_check_range( &ctx->X, &ctx->P ) != 0 );
MPI_CHK( mpi_exp_mod( &ctx->GX, &ctx->G, &ctx->X,
&ctx->P , &ctx->RP ) );
if( ( ret = dhm_check_range( &ctx->GX, &ctx->P ) ) != 0 )
return( ret );
MPI_CHK( mpi_write_binary( &ctx->GX, output, olen ) );
cleanup:
if( ret != 0 )
return( POLARSSL_ERR_DHM_MAKE_PUBLIC_FAILED + ret );
return( 0 );
}
/*
* Derive and export the shared secret (G^Y)^X mod P
*/
int dhm_calc_secret( dhm_context *ctx,
unsigned char *output, size_t *olen )
{
int ret;
if( ctx == NULL || *olen < ctx->len )
return( POLARSSL_ERR_DHM_BAD_INPUT_DATA );
MPI_CHK( mpi_exp_mod( &ctx->K, &ctx->GY, &ctx->X,
&ctx->P, &ctx->RP ) );
if( ( ret = dhm_check_range( &ctx->GY, &ctx->P ) ) != 0 )
return( ret );
*olen = mpi_size( &ctx->K );
MPI_CHK( mpi_write_binary( &ctx->K, output, *olen ) );
cleanup:
if( ret != 0 )
return( POLARSSL_ERR_DHM_CALC_SECRET_FAILED + ret );
return( 0 );
}
/*
* Free the components of a DHM key
*/
void dhm_free( dhm_context *ctx )
{
mpi_free( &ctx->RP ); mpi_free( &ctx->K ); mpi_free( &ctx->GY );
mpi_free( &ctx->GX ); mpi_free( &ctx->X ); mpi_free( &ctx->G );
mpi_free( &ctx->P );
}
#if defined(POLARSSL_SELF_TEST)
/*
* Checkup routine
*/
int dhm_self_test( int verbose )
{
return( verbose++ );
}
#endif
#endif
-204
View File
@@ -1,204 +0,0 @@
/*
* Entropy accumulator implementation
*
* Copyright (C) 2006-2011, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_ENTROPY_C)
#include "polarssl/entropy.h"
#include "polarssl/entropy_poll.h"
#if defined(POLARSSL_HAVEGE_C)
#include "polarssl/havege.h"
#endif
#define ENTROPY_MAX_LOOP 256 /**< Maximum amount to loop before error */
void entropy_init( entropy_context *ctx )
{
memset( ctx, 0, sizeof(entropy_context) );
sha4_starts( &ctx->accumulator, 0 );
#if defined(POLARSSL_HAVEGE_C)
havege_init( &ctx->havege_data );
#endif
#if !defined(POLARSSL_NO_DEFAULT_ENTROPY_SOURCES)
#if !defined(POLARSSL_NO_PLATFORM_ENTROPY)
entropy_add_source( ctx, platform_entropy_poll, NULL,
ENTROPY_MIN_PLATFORM );
#endif
#if defined(POLARSSL_TIMING_C)
entropy_add_source( ctx, hardclock_poll, NULL, ENTROPY_MIN_HARDCLOCK );
#endif
#if defined(POLARSSL_HAVEGE_C)
entropy_add_source( ctx, havege_poll, &ctx->havege_data,
ENTROPY_MIN_HAVEGE );
#endif
#endif /* POLARSSL_NO_DEFAULT_ENTROPY_SOURCES */
}
int entropy_add_source( entropy_context *ctx,
f_source_ptr f_source, void *p_source,
size_t threshold )
{
int index = ctx->source_count;
if( index >= ENTROPY_MAX_SOURCES )
return( POLARSSL_ERR_ENTROPY_MAX_SOURCES );
ctx->source[index].f_source = f_source;
ctx->source[index].p_source = p_source;
ctx->source[index].threshold = threshold;
ctx->source_count++;
return( 0 );
}
/*
* Entropy accumulator update
*/
int entropy_update( entropy_context *ctx, unsigned char source_id,
const unsigned char *data, size_t len )
{
unsigned char header[2];
unsigned char tmp[ENTROPY_BLOCK_SIZE];
size_t use_len = len;
const unsigned char *p = data;
if( use_len > ENTROPY_BLOCK_SIZE )
{
sha4( data, len, tmp, 0 );
p = tmp;
use_len = ENTROPY_BLOCK_SIZE;
}
header[0] = source_id;
header[1] = use_len & 0xFF;
sha4_update( &ctx->accumulator, header, 2 );
sha4_update( &ctx->accumulator, p, use_len );
return( 0 );
}
int entropy_update_manual( entropy_context *ctx,
const unsigned char *data, size_t len )
{
return entropy_update( ctx, ENTROPY_SOURCE_MANUAL, data, len );
}
/*
* Run through the different sources to add entropy to our accumulator
*/
int entropy_gather( entropy_context *ctx )
{
int ret, i;
unsigned char buf[ENTROPY_MAX_GATHER];
size_t olen;
if( ctx->source_count == 0 )
return( POLARSSL_ERR_ENTROPY_NO_SOURCES_DEFINED );
/*
* Run through our entropy sources
*/
for( i = 0; i < ctx->source_count; i++ )
{
olen = 0;
if ( ( ret = ctx->source[i].f_source( ctx->source[i].p_source,
buf, ENTROPY_MAX_GATHER, &olen ) ) != 0 )
{
return( ret );
}
/*
* Add if we actually gathered something
*/
if( olen > 0 )
{
entropy_update( ctx, (unsigned char) i, buf, olen );
ctx->source[i].size += olen;
}
}
return( 0 );
}
int entropy_func( void *data, unsigned char *output, size_t len )
{
int ret, count = 0, i, reached;
entropy_context *ctx = (entropy_context *) data;
unsigned char buf[ENTROPY_BLOCK_SIZE];
if( len > ENTROPY_BLOCK_SIZE )
return( POLARSSL_ERR_ENTROPY_SOURCE_FAILED );
/*
* Always gather extra entropy before a call
*/
do
{
if( count++ > ENTROPY_MAX_LOOP )
return( POLARSSL_ERR_ENTROPY_SOURCE_FAILED );
if( ( ret = entropy_gather( ctx ) ) != 0 )
return( ret );
reached = 0;
for( i = 0; i < ctx->source_count; i++ )
if( ctx->source[i].size >= ctx->source[i].threshold )
reached++;
}
while( reached != ctx->source_count );
memset( buf, 0, ENTROPY_BLOCK_SIZE );
sha4_finish( &ctx->accumulator, buf );
/*
* Perform second SHA-512 on entropy
*/
sha4( buf, ENTROPY_BLOCK_SIZE, buf, 0 );
/*
* Reset accumulator and counters and recycle existing entropy
*/
memset( &ctx->accumulator, 0, sizeof( sha4_context ) );
sha4_starts( &ctx->accumulator, 0 );
sha4_update( &ctx->accumulator, buf, ENTROPY_BLOCK_SIZE );
for( i = 0; i < ctx->source_count; i++ )
ctx->source[i].size = 0;
memcpy( output, buf, len );
return( 0 );
}
#endif
-136
View File
@@ -1,136 +0,0 @@
/*
* Platform-specific and custom entropy polling functions
*
* Copyright (C) 2006-2011, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_ENTROPY_C)
#include "polarssl/entropy.h"
#include "polarssl/entropy_poll.h"
#if defined(POLARSSL_TIMING_C)
#include "polarssl/timing.h"
#endif
#if defined(POLARSSL_HAVEGE_C)
#include "polarssl/havege.h"
#endif
#if !defined(POLARSSL_NO_PLATFORM_ENTROPY)
#if defined(_WIN32)
#if !defined(_WIN32_WINNT)
#define _WIN32_WINNT 0x0400
#endif
#include <windows.h>
#include <wincrypt.h>
int platform_entropy_poll( void *data, unsigned char *output, size_t len,
size_t *olen )
{
HCRYPTPROV provider;
((void) data);
*olen = 0;
if( CryptAcquireContext( &provider, NULL, NULL,
PROV_RSA_FULL, CRYPT_VERIFYCONTEXT ) == FALSE )
{
return POLARSSL_ERR_ENTROPY_SOURCE_FAILED;
}
if( CryptGenRandom( provider, len, output ) == FALSE )
return POLARSSL_ERR_ENTROPY_SOURCE_FAILED;
CryptReleaseContext( provider, 0 );
*olen = len;
return( 0 );
}
#else
#include <stdio.h>
int platform_entropy_poll( void *data,
unsigned char *output, size_t len, size_t *olen )
{
FILE *file;
size_t ret;
((void) data);
*olen = 0;
file = fopen( "/dev/urandom", "rb" );
if( file == NULL )
return POLARSSL_ERR_ENTROPY_SOURCE_FAILED;
ret = fread( output, 1, len, file );
if( ret != len )
{
fclose( file );
return POLARSSL_ERR_ENTROPY_SOURCE_FAILED;
}
fclose( file );
*olen = len;
return( 0 );
}
#endif
#endif
#if defined(POLARSSL_TIMING_C)
int hardclock_poll( void *data,
unsigned char *output, size_t len, size_t *olen )
{
unsigned long timer = hardclock();
((void) data);
*olen = 0;
if( len < sizeof(unsigned long) )
return( 0 );
memcpy( output, &timer, sizeof(unsigned long) );
*olen = sizeof(unsigned long);
return( 0 );
}
#endif
#if defined(POLARSSL_HAVEGE_C)
int havege_poll( void *data,
unsigned char *output, size_t len, size_t *olen )
{
havege_state *hs = (havege_state *) data;
*olen = 0;
if( havege_random( hs, output, len ) != 0 )
return POLARSSL_ERR_ENTROPY_SOURCE_FAILED;
*olen = len;
return( 0 );
}
#endif
#endif /* POLARSSL_ENTROPY_C */
-612
View File
@@ -1,612 +0,0 @@
/*
* Error message information
*
* Copyright (C) 2006-2012, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_ERROR_C)
#include "polarssl/error.h"
#if defined(POLARSSL_AES_C)
#include "polarssl/aes.h"
#endif
#if defined(POLARSSL_BASE64_C)
#include "polarssl/base64.h"
#endif
#if defined(POLARSSL_BIGNUM_C)
#include "polarssl/bignum.h"
#endif
#if defined(POLARSSL_BLOWFISH_C)
#include "polarssl/blowfish.h"
#endif
#if defined(POLARSSL_CAMELLIA_C)
#include "polarssl/camellia.h"
#endif
#if defined(POLARSSL_CIPHER_C)
#include "polarssl/cipher.h"
#endif
#if defined(POLARSSL_CTR_DRBG_C)
#include "polarssl/ctr_drbg.h"
#endif
#if defined(POLARSSL_DES_C)
#include "polarssl/des.h"
#endif
#if defined(POLARSSL_DHM_C)
#include "polarssl/dhm.h"
#endif
#if defined(POLARSSL_ENTROPY_C)
#include "polarssl/entropy.h"
#endif
#if defined(POLARSSL_GCM_C)
#include "polarssl/gcm.h"
#endif
#if defined(POLARSSL_MD_C)
#include "polarssl/md.h"
#endif
#if defined(POLARSSL_MD2_C)
#include "polarssl/md2.h"
#endif
#if defined(POLARSSL_MD4_C)
#include "polarssl/md4.h"
#endif
#if defined(POLARSSL_MD5_C)
#include "polarssl/md5.h"
#endif
#if defined(POLARSSL_NET_C)
#include "polarssl/net.h"
#endif
#if defined(POLARSSL_PADLOCK_C)
#include "polarssl/padlock.h"
#endif
#if defined(POLARSSL_PBKDF2_C)
#include "polarssl/pbkdf2.h"
#endif
#if defined(POLARSSL_PEM_C)
#include "polarssl/pem.h"
#endif
#if defined(POLARSSL_PKCS12_C)
#include "polarssl/pkcs12.h"
#endif
#if defined(POLARSSL_PKCS5_C)
#include "polarssl/pkcs5.h"
#endif
#if defined(POLARSSL_RSA_C)
#include "polarssl/rsa.h"
#endif
#if defined(POLARSSL_SHA1_C)
#include "polarssl/sha1.h"
#endif
#if defined(POLARSSL_SHA2_C)
#include "polarssl/sha2.h"
#endif
#if defined(POLARSSL_SHA4_C)
#include "polarssl/sha4.h"
#endif
#if defined(POLARSSL_SSL_TLS_C)
#include "polarssl/ssl.h"
#endif
#if defined(POLARSSL_X509_PARSE_C)
#include "polarssl/x509.h"
#endif
#if defined(POLARSSL_XTEA_C)
#include "polarssl/xtea.h"
#endif
#include <string.h>
#if defined _MSC_VER && !defined snprintf
#define snprintf _snprintf
#endif
void error_strerror( int ret, char *buf, size_t buflen )
{
size_t len;
int use_ret;
memset( buf, 0x00, buflen );
if( ret < 0 )
ret = -ret;
if( ret & 0xFF80 )
{
use_ret = ret & 0xFF80;
// High level error codes
//
#if defined(POLARSSL_CIPHER_C)
if( use_ret == -(POLARSSL_ERR_CIPHER_FEATURE_UNAVAILABLE) )
snprintf( buf, buflen, "CIPHER - The selected feature is not available" );
if( use_ret == -(POLARSSL_ERR_CIPHER_BAD_INPUT_DATA) )
snprintf( buf, buflen, "CIPHER - Bad input parameters to function" );
if( use_ret == -(POLARSSL_ERR_CIPHER_ALLOC_FAILED) )
snprintf( buf, buflen, "CIPHER - Failed to allocate memory" );
if( use_ret == -(POLARSSL_ERR_CIPHER_INVALID_PADDING) )
snprintf( buf, buflen, "CIPHER - Input data contains invalid padding and is rejected" );
if( use_ret == -(POLARSSL_ERR_CIPHER_FULL_BLOCK_EXPECTED) )
snprintf( buf, buflen, "CIPHER - Decryption of block requires a full block" );
#endif /* POLARSSL_CIPHER_C */
#if defined(POLARSSL_DHM_C)
if( use_ret == -(POLARSSL_ERR_DHM_BAD_INPUT_DATA) )
snprintf( buf, buflen, "DHM - Bad input parameters to function" );
if( use_ret == -(POLARSSL_ERR_DHM_READ_PARAMS_FAILED) )
snprintf( buf, buflen, "DHM - Reading of the DHM parameters failed" );
if( use_ret == -(POLARSSL_ERR_DHM_MAKE_PARAMS_FAILED) )
snprintf( buf, buflen, "DHM - Making of the DHM parameters failed" );
if( use_ret == -(POLARSSL_ERR_DHM_READ_PUBLIC_FAILED) )
snprintf( buf, buflen, "DHM - Reading of the public values failed" );
if( use_ret == -(POLARSSL_ERR_DHM_MAKE_PUBLIC_FAILED) )
snprintf( buf, buflen, "DHM - Making of the public value failed" );
if( use_ret == -(POLARSSL_ERR_DHM_CALC_SECRET_FAILED) )
snprintf( buf, buflen, "DHM - Calculation of the DHM secret failed" );
#endif /* POLARSSL_DHM_C */
#if defined(POLARSSL_MD_C)
if( use_ret == -(POLARSSL_ERR_MD_FEATURE_UNAVAILABLE) )
snprintf( buf, buflen, "MD - The selected feature is not available" );
if( use_ret == -(POLARSSL_ERR_MD_BAD_INPUT_DATA) )
snprintf( buf, buflen, "MD - Bad input parameters to function" );
if( use_ret == -(POLARSSL_ERR_MD_ALLOC_FAILED) )
snprintf( buf, buflen, "MD - Failed to allocate memory" );
if( use_ret == -(POLARSSL_ERR_MD_FILE_IO_ERROR) )
snprintf( buf, buflen, "MD - Opening or reading of file failed" );
#endif /* POLARSSL_MD_C */
#if defined(POLARSSL_PEM_C)
if( use_ret == -(POLARSSL_ERR_PEM_NO_HEADER_FOOTER_PRESENT) )
snprintf( buf, buflen, "PEM - No PEM header or footer found" );
if( use_ret == -(POLARSSL_ERR_PEM_INVALID_DATA) )
snprintf( buf, buflen, "PEM - PEM string is not as expected" );
if( use_ret == -(POLARSSL_ERR_PEM_MALLOC_FAILED) )
snprintf( buf, buflen, "PEM - Failed to allocate memory" );
if( use_ret == -(POLARSSL_ERR_PEM_INVALID_ENC_IV) )
snprintf( buf, buflen, "PEM - RSA IV is not in hex-format" );
if( use_ret == -(POLARSSL_ERR_PEM_UNKNOWN_ENC_ALG) )
snprintf( buf, buflen, "PEM - Unsupported key encryption algorithm" );
if( use_ret == -(POLARSSL_ERR_PEM_PASSWORD_REQUIRED) )
snprintf( buf, buflen, "PEM - Private key password can't be empty" );
if( use_ret == -(POLARSSL_ERR_PEM_PASSWORD_MISMATCH) )
snprintf( buf, buflen, "PEM - Given private key password does not allow for correct decryption" );
if( use_ret == -(POLARSSL_ERR_PEM_FEATURE_UNAVAILABLE) )
snprintf( buf, buflen, "PEM - Unavailable feature, e.g. hashing/encryption combination" );
if( use_ret == -(POLARSSL_ERR_PEM_BAD_INPUT_DATA) )
snprintf( buf, buflen, "PEM - Bad input parameters to function" );
#endif /* POLARSSL_PEM_C */
#if defined(POLARSSL_PKCS12_C)
if( use_ret == -(POLARSSL_ERR_PKCS12_BAD_INPUT_DATA) )
snprintf( buf, buflen, "PKCS12 - Bad input parameters to function" );
if( use_ret == -(POLARSSL_ERR_PKCS12_FEATURE_UNAVAILABLE) )
snprintf( buf, buflen, "PKCS12 - Feature not available, e.g. unsupported encryption scheme" );
if( use_ret == -(POLARSSL_ERR_PKCS12_PBE_INVALID_FORMAT) )
snprintf( buf, buflen, "PKCS12 - PBE ASN.1 data not as expected" );
if( use_ret == -(POLARSSL_ERR_PKCS12_PASSWORD_MISMATCH) )
snprintf( buf, buflen, "PKCS12 - Given private key password does not allow for correct decryption" );
#endif /* POLARSSL_PKCS12_C */
#if defined(POLARSSL_PKCS5_C)
if( use_ret == -(POLARSSL_ERR_PKCS5_BAD_INPUT_DATA) )
snprintf( buf, buflen, "PKCS5 - Bad input parameters to function" );
if( use_ret == -(POLARSSL_ERR_PKCS5_INVALID_FORMAT) )
snprintf( buf, buflen, "PKCS5 - Unexpected ASN.1 data" );
if( use_ret == -(POLARSSL_ERR_PKCS5_FEATURE_UNAVAILABLE) )
snprintf( buf, buflen, "PKCS5 - Requested encryption or digest alg not available" );
if( use_ret == -(POLARSSL_ERR_PKCS5_PASSWORD_MISMATCH) )
snprintf( buf, buflen, "PKCS5 - Given private key password does not allow for correct decryption" );
#endif /* POLARSSL_PKCS5_C */
#if defined(POLARSSL_RSA_C)
if( use_ret == -(POLARSSL_ERR_RSA_BAD_INPUT_DATA) )
snprintf( buf, buflen, "RSA - Bad input parameters to function" );
if( use_ret == -(POLARSSL_ERR_RSA_INVALID_PADDING) )
snprintf( buf, buflen, "RSA - Input data contains invalid padding and is rejected" );
if( use_ret == -(POLARSSL_ERR_RSA_KEY_GEN_FAILED) )
snprintf( buf, buflen, "RSA - Something failed during generation of a key" );
if( use_ret == -(POLARSSL_ERR_RSA_KEY_CHECK_FAILED) )
snprintf( buf, buflen, "RSA - Key failed to pass the libraries validity check" );
if( use_ret == -(POLARSSL_ERR_RSA_PUBLIC_FAILED) )
snprintf( buf, buflen, "RSA - The public key operation failed" );
if( use_ret == -(POLARSSL_ERR_RSA_PRIVATE_FAILED) )
snprintf( buf, buflen, "RSA - The private key operation failed" );
if( use_ret == -(POLARSSL_ERR_RSA_VERIFY_FAILED) )
snprintf( buf, buflen, "RSA - The PKCS#1 verification failed" );
if( use_ret == -(POLARSSL_ERR_RSA_OUTPUT_TOO_LARGE) )
snprintf( buf, buflen, "RSA - The output buffer for decryption is not large enough" );
if( use_ret == -(POLARSSL_ERR_RSA_RNG_FAILED) )
snprintf( buf, buflen, "RSA - The random generator failed to generate non-zeros" );
#endif /* POLARSSL_RSA_C */
#if defined(POLARSSL_SSL_TLS_C)
if( use_ret == -(POLARSSL_ERR_SSL_FEATURE_UNAVAILABLE) )
snprintf( buf, buflen, "SSL - The requested feature is not available" );
if( use_ret == -(POLARSSL_ERR_SSL_BAD_INPUT_DATA) )
snprintf( buf, buflen, "SSL - Bad input parameters to function" );
if( use_ret == -(POLARSSL_ERR_SSL_INVALID_MAC) )
snprintf( buf, buflen, "SSL - Verification of the message MAC failed" );
if( use_ret == -(POLARSSL_ERR_SSL_INVALID_RECORD) )
snprintf( buf, buflen, "SSL - An invalid SSL record was received" );
if( use_ret == -(POLARSSL_ERR_SSL_CONN_EOF) )
snprintf( buf, buflen, "SSL - The connection indicated an EOF" );
if( use_ret == -(POLARSSL_ERR_SSL_UNKNOWN_CIPHER) )
snprintf( buf, buflen, "SSL - An unknown cipher was received" );
if( use_ret == -(POLARSSL_ERR_SSL_NO_CIPHER_CHOSEN) )
snprintf( buf, buflen, "SSL - The server has no ciphersuites in common with the client" );
if( use_ret == -(POLARSSL_ERR_SSL_NO_SESSION_FOUND) )
snprintf( buf, buflen, "SSL - No session to recover was found" );
if( use_ret == -(POLARSSL_ERR_SSL_NO_CLIENT_CERTIFICATE) )
snprintf( buf, buflen, "SSL - No client certification received from the client, but required by the authentication mode" );
if( use_ret == -(POLARSSL_ERR_SSL_CERTIFICATE_TOO_LARGE) )
snprintf( buf, buflen, "SSL - DESCRIPTION MISSING" );
if( use_ret == -(POLARSSL_ERR_SSL_CERTIFICATE_REQUIRED) )
snprintf( buf, buflen, "SSL - The own certificate is not set, but needed by the server" );
if( use_ret == -(POLARSSL_ERR_SSL_PRIVATE_KEY_REQUIRED) )
snprintf( buf, buflen, "SSL - The own private key is not set, but needed" );
if( use_ret == -(POLARSSL_ERR_SSL_CA_CHAIN_REQUIRED) )
snprintf( buf, buflen, "SSL - No CA Chain is set, but required to operate" );
if( use_ret == -(POLARSSL_ERR_SSL_UNEXPECTED_MESSAGE) )
snprintf( buf, buflen, "SSL - An unexpected message was received from our peer" );
if( use_ret == -(POLARSSL_ERR_SSL_FATAL_ALERT_MESSAGE) )
{
snprintf( buf, buflen, "SSL - A fatal alert message was received from our peer" );
return;
}
if( use_ret == -(POLARSSL_ERR_SSL_PEER_VERIFY_FAILED) )
snprintf( buf, buflen, "SSL - Verification of our peer failed" );
if( use_ret == -(POLARSSL_ERR_SSL_PEER_CLOSE_NOTIFY) )
snprintf( buf, buflen, "SSL - The peer notified us that the connection is going to be closed" );
if( use_ret == -(POLARSSL_ERR_SSL_BAD_HS_CLIENT_HELLO) )
snprintf( buf, buflen, "SSL - Processing of the ClientHello handshake message failed" );
if( use_ret == -(POLARSSL_ERR_SSL_BAD_HS_SERVER_HELLO) )
snprintf( buf, buflen, "SSL - Processing of the ServerHello handshake message failed" );
if( use_ret == -(POLARSSL_ERR_SSL_BAD_HS_CERTIFICATE) )
snprintf( buf, buflen, "SSL - Processing of the Certificate handshake message failed" );
if( use_ret == -(POLARSSL_ERR_SSL_BAD_HS_CERTIFICATE_REQUEST) )
snprintf( buf, buflen, "SSL - Processing of the CertificateRequest handshake message failed" );
if( use_ret == -(POLARSSL_ERR_SSL_BAD_HS_SERVER_KEY_EXCHANGE) )
snprintf( buf, buflen, "SSL - Processing of the ServerKeyExchange handshake message failed" );
if( use_ret == -(POLARSSL_ERR_SSL_BAD_HS_SERVER_HELLO_DONE) )
snprintf( buf, buflen, "SSL - Processing of the ServerHelloDone handshake message failed" );
if( use_ret == -(POLARSSL_ERR_SSL_BAD_HS_CLIENT_KEY_EXCHANGE) )
snprintf( buf, buflen, "SSL - Processing of the ClientKeyExchange handshake message failed" );
if( use_ret == -(POLARSSL_ERR_SSL_BAD_HS_CLIENT_KEY_EXCHANGE_DHM_RP) )
snprintf( buf, buflen, "SSL - Processing of the ClientKeyExchange handshake message failed in DHM Read Public" );
if( use_ret == -(POLARSSL_ERR_SSL_BAD_HS_CLIENT_KEY_EXCHANGE_DHM_CS) )
snprintf( buf, buflen, "SSL - Processing of the ClientKeyExchange handshake message failed in DHM Calculate Secret" );
if( use_ret == -(POLARSSL_ERR_SSL_BAD_HS_CERTIFICATE_VERIFY) )
snprintf( buf, buflen, "SSL - Processing of the CertificateVerify handshake message failed" );
if( use_ret == -(POLARSSL_ERR_SSL_BAD_HS_CHANGE_CIPHER_SPEC) )
snprintf( buf, buflen, "SSL - Processing of the ChangeCipherSpec handshake message failed" );
if( use_ret == -(POLARSSL_ERR_SSL_BAD_HS_FINISHED) )
snprintf( buf, buflen, "SSL - Processing of the Finished handshake message failed" );
if( use_ret == -(POLARSSL_ERR_SSL_MALLOC_FAILED) )
snprintf( buf, buflen, "SSL - Memory allocation failed" );
if( use_ret == -(POLARSSL_ERR_SSL_HW_ACCEL_FAILED) )
snprintf( buf, buflen, "SSL - Hardware acceleration function returned with error" );
if( use_ret == -(POLARSSL_ERR_SSL_HW_ACCEL_FALLTHROUGH) )
snprintf( buf, buflen, "SSL - Hardware acceleration function skipped / left alone data" );
if( use_ret == -(POLARSSL_ERR_SSL_COMPRESSION_FAILED) )
snprintf( buf, buflen, "SSL - Processing of the compression / decompression failed" );
if( use_ret == -(POLARSSL_ERR_SSL_BAD_HS_PROTOCOL_VERSION) )
snprintf( buf, buflen, "SSL - Handshake protocol not within min/max boundaries" );
#endif /* POLARSSL_SSL_TLS_C */
#if defined(POLARSSL_X509_PARSE_C)
if( use_ret == -(POLARSSL_ERR_X509_FEATURE_UNAVAILABLE) )
snprintf( buf, buflen, "X509 - Unavailable feature, e.g. RSA hashing/encryption combination" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_INVALID_PEM) )
snprintf( buf, buflen, "X509 - The PEM-encoded certificate contains invalid elements, e.g. invalid character" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_INVALID_FORMAT) )
snprintf( buf, buflen, "X509 - The certificate format is invalid, e.g. different type expected" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_INVALID_VERSION) )
snprintf( buf, buflen, "X509 - The certificate version element is invalid" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_INVALID_SERIAL) )
snprintf( buf, buflen, "X509 - The serial tag or value is invalid" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_INVALID_ALG) )
snprintf( buf, buflen, "X509 - The algorithm tag or value is invalid" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_INVALID_NAME) )
snprintf( buf, buflen, "X509 - The name tag or value is invalid" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_INVALID_DATE) )
snprintf( buf, buflen, "X509 - The date tag or value is invalid" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_INVALID_PUBKEY) )
snprintf( buf, buflen, "X509 - The pubkey tag or value is invalid (only RSA is supported)" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_INVALID_SIGNATURE) )
snprintf( buf, buflen, "X509 - The signature tag or value invalid" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_INVALID_EXTENSIONS) )
snprintf( buf, buflen, "X509 - The extension tag or value is invalid" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_UNKNOWN_VERSION) )
snprintf( buf, buflen, "X509 - Certificate or CRL has an unsupported version number" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_UNKNOWN_SIG_ALG) )
snprintf( buf, buflen, "X509 - Signature algorithm (oid) is unsupported" );
if( use_ret == -(POLARSSL_ERR_X509_UNKNOWN_PK_ALG) )
snprintf( buf, buflen, "X509 - Key algorithm is unsupported (only RSA is supported)" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_SIG_MISMATCH) )
snprintf( buf, buflen, "X509 - Certificate signature algorithms do not match. (see \\c ::x509_cert sig_oid)" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_VERIFY_FAILED) )
snprintf( buf, buflen, "X509 - Certificate verification failed, e.g. CRL, CA or signature check failed" );
if( use_ret == -(POLARSSL_ERR_X509_KEY_INVALID_VERSION) )
snprintf( buf, buflen, "X509 - Unsupported RSA key version" );
if( use_ret == -(POLARSSL_ERR_X509_KEY_INVALID_FORMAT) )
snprintf( buf, buflen, "X509 - Invalid RSA key tag or value" );
if( use_ret == -(POLARSSL_ERR_X509_CERT_UNKNOWN_FORMAT) )
snprintf( buf, buflen, "X509 - Format not recognized as DER or PEM" );
if( use_ret == -(POLARSSL_ERR_X509_INVALID_INPUT) )
snprintf( buf, buflen, "X509 - Input invalid" );
if( use_ret == -(POLARSSL_ERR_X509_MALLOC_FAILED) )
snprintf( buf, buflen, "X509 - Allocation of memory failed" );
if( use_ret == -(POLARSSL_ERR_X509_FILE_IO_ERROR) )
snprintf( buf, buflen, "X509 - Read/write of file failed" );
if( use_ret == -(POLARSSL_ERR_X509_PASSWORD_REQUIRED) )
snprintf( buf, buflen, "X509 - Private key password can't be empty" );
if( use_ret == -(POLARSSL_ERR_X509_PASSWORD_MISMATCH) )
snprintf( buf, buflen, "X509 - Given private key password does not allow for correct decryption" );
#endif /* POLARSSL_X509_PARSE_C */
if( strlen( buf ) == 0 )
snprintf( buf, buflen, "UNKNOWN ERROR CODE (%04X)", use_ret );
}
use_ret = ret & ~0xFF80;
if( use_ret == 0 )
return;
// If high level code is present, make a concatenation between both
// error strings.
//
len = strlen( buf );
if( len > 0 )
{
if( buflen - len < 5 )
return;
snprintf( buf + len, buflen - len, " : " );
buf += len + 3;
buflen -= len + 3;
}
// Low level error codes
//
#if defined(POLARSSL_AES_C)
if( use_ret == -(POLARSSL_ERR_AES_INVALID_KEY_LENGTH) )
snprintf( buf, buflen, "AES - Invalid key length" );
if( use_ret == -(POLARSSL_ERR_AES_INVALID_INPUT_LENGTH) )
snprintf( buf, buflen, "AES - Invalid data input length" );
#endif /* POLARSSL_AES_C */
#if defined(POLARSSL_ASN1_PARSE_C)
if( use_ret == -(POLARSSL_ERR_ASN1_OUT_OF_DATA) )
snprintf( buf, buflen, "ASN1 - Out of data when parsing an ASN1 data structure" );
if( use_ret == -(POLARSSL_ERR_ASN1_UNEXPECTED_TAG) )
snprintf( buf, buflen, "ASN1 - ASN1 tag was of an unexpected value" );
if( use_ret == -(POLARSSL_ERR_ASN1_INVALID_LENGTH) )
snprintf( buf, buflen, "ASN1 - Error when trying to determine the length or invalid length" );
if( use_ret == -(POLARSSL_ERR_ASN1_LENGTH_MISMATCH) )
snprintf( buf, buflen, "ASN1 - Actual length differs from expected length" );
if( use_ret == -(POLARSSL_ERR_ASN1_INVALID_DATA) )
snprintf( buf, buflen, "ASN1 - Data is invalid. (not used)" );
if( use_ret == -(POLARSSL_ERR_ASN1_MALLOC_FAILED) )
snprintf( buf, buflen, "ASN1 - Memory allocation failed" );
if( use_ret == -(POLARSSL_ERR_ASN1_BUF_TOO_SMALL) )
snprintf( buf, buflen, "ASN1 - Buffer too small when writing ASN.1 data structure" );
#endif /* POLARSSL_ASN1_PARSE_C */
#if defined(POLARSSL_BASE64_C)
if( use_ret == -(POLARSSL_ERR_BASE64_BUFFER_TOO_SMALL) )
snprintf( buf, buflen, "BASE64 - Output buffer too small" );
if( use_ret == -(POLARSSL_ERR_BASE64_INVALID_CHARACTER) )
snprintf( buf, buflen, "BASE64 - Invalid character in input" );
#endif /* POLARSSL_BASE64_C */
#if defined(POLARSSL_BIGNUM_C)
if( use_ret == -(POLARSSL_ERR_MPI_FILE_IO_ERROR) )
snprintf( buf, buflen, "BIGNUM - An error occurred while reading from or writing to a file" );
if( use_ret == -(POLARSSL_ERR_MPI_BAD_INPUT_DATA) )
snprintf( buf, buflen, "BIGNUM - Bad input parameters to function" );
if( use_ret == -(POLARSSL_ERR_MPI_INVALID_CHARACTER) )
snprintf( buf, buflen, "BIGNUM - There is an invalid character in the digit string" );
if( use_ret == -(POLARSSL_ERR_MPI_BUFFER_TOO_SMALL) )
snprintf( buf, buflen, "BIGNUM - The buffer is too small to write to" );
if( use_ret == -(POLARSSL_ERR_MPI_NEGATIVE_VALUE) )
snprintf( buf, buflen, "BIGNUM - The input arguments are negative or result in illegal output" );
if( use_ret == -(POLARSSL_ERR_MPI_DIVISION_BY_ZERO) )
snprintf( buf, buflen, "BIGNUM - The input argument for division is zero, which is not allowed" );
if( use_ret == -(POLARSSL_ERR_MPI_NOT_ACCEPTABLE) )
snprintf( buf, buflen, "BIGNUM - The input arguments are not acceptable" );
if( use_ret == -(POLARSSL_ERR_MPI_MALLOC_FAILED) )
snprintf( buf, buflen, "BIGNUM - Memory allocation failed" );
#endif /* POLARSSL_BIGNUM_C */
#if defined(POLARSSL_BLOWFISH_C)
if( use_ret == -(POLARSSL_ERR_BLOWFISH_INVALID_KEY_LENGTH) )
snprintf( buf, buflen, "BLOWFISH - Invalid key length" );
if( use_ret == -(POLARSSL_ERR_BLOWFISH_INVALID_INPUT_LENGTH) )
snprintf( buf, buflen, "BLOWFISH - Invalid data input length" );
#endif /* POLARSSL_BLOWFISH_C */
#if defined(POLARSSL_CAMELLIA_C)
if( use_ret == -(POLARSSL_ERR_CAMELLIA_INVALID_KEY_LENGTH) )
snprintf( buf, buflen, "CAMELLIA - Invalid key length" );
if( use_ret == -(POLARSSL_ERR_CAMELLIA_INVALID_INPUT_LENGTH) )
snprintf( buf, buflen, "CAMELLIA - Invalid data input length" );
#endif /* POLARSSL_CAMELLIA_C */
#if defined(POLARSSL_CTR_DRBG_C)
if( use_ret == -(POLARSSL_ERR_CTR_DRBG_ENTROPY_SOURCE_FAILED) )
snprintf( buf, buflen, "CTR_DRBG - The entropy source failed" );
if( use_ret == -(POLARSSL_ERR_CTR_DRBG_REQUEST_TOO_BIG) )
snprintf( buf, buflen, "CTR_DRBG - Too many random requested in single call" );
if( use_ret == -(POLARSSL_ERR_CTR_DRBG_INPUT_TOO_BIG) )
snprintf( buf, buflen, "CTR_DRBG - Input too large (Entropy + additional)" );
if( use_ret == -(POLARSSL_ERR_CTR_DRBG_FILE_IO_ERROR) )
snprintf( buf, buflen, "CTR_DRBG - Read/write error in file" );
#endif /* POLARSSL_CTR_DRBG_C */
#if defined(POLARSSL_DES_C)
if( use_ret == -(POLARSSL_ERR_DES_INVALID_INPUT_LENGTH) )
snprintf( buf, buflen, "DES - The data input has an invalid length" );
#endif /* POLARSSL_DES_C */
#if defined(POLARSSL_ENTROPY_C)
if( use_ret == -(POLARSSL_ERR_ENTROPY_SOURCE_FAILED) )
snprintf( buf, buflen, "ENTROPY - Critical entropy source failure" );
if( use_ret == -(POLARSSL_ERR_ENTROPY_MAX_SOURCES) )
snprintf( buf, buflen, "ENTROPY - No more sources can be added" );
if( use_ret == -(POLARSSL_ERR_ENTROPY_NO_SOURCES_DEFINED) )
snprintf( buf, buflen, "ENTROPY - No sources have been added to poll" );
#endif /* POLARSSL_ENTROPY_C */
#if defined(POLARSSL_GCM_C)
if( use_ret == -(POLARSSL_ERR_GCM_AUTH_FAILED) )
snprintf( buf, buflen, "GCM - Authenticated decryption failed" );
if( use_ret == -(POLARSSL_ERR_GCM_BAD_INPUT) )
snprintf( buf, buflen, "GCM - Bad input parameters to function" );
#endif /* POLARSSL_GCM_C */
#if defined(POLARSSL_MD2_C)
if( use_ret == -(POLARSSL_ERR_MD2_FILE_IO_ERROR) )
snprintf( buf, buflen, "MD2 - Read/write error in file" );
#endif /* POLARSSL_MD2_C */
#if defined(POLARSSL_MD4_C)
if( use_ret == -(POLARSSL_ERR_MD4_FILE_IO_ERROR) )
snprintf( buf, buflen, "MD4 - Read/write error in file" );
#endif /* POLARSSL_MD4_C */
#if defined(POLARSSL_MD5_C)
if( use_ret == -(POLARSSL_ERR_MD5_FILE_IO_ERROR) )
snprintf( buf, buflen, "MD5 - Read/write error in file" );
#endif /* POLARSSL_MD5_C */
#if defined(POLARSSL_NET_C)
if( use_ret == -(POLARSSL_ERR_NET_UNKNOWN_HOST) )
snprintf( buf, buflen, "NET - Failed to get an IP address for the given hostname" );
if( use_ret == -(POLARSSL_ERR_NET_SOCKET_FAILED) )
snprintf( buf, buflen, "NET - Failed to open a socket" );
if( use_ret == -(POLARSSL_ERR_NET_CONNECT_FAILED) )
snprintf( buf, buflen, "NET - The connection to the given server / port failed" );
if( use_ret == -(POLARSSL_ERR_NET_BIND_FAILED) )
snprintf( buf, buflen, "NET - Binding of the socket failed" );
if( use_ret == -(POLARSSL_ERR_NET_LISTEN_FAILED) )
snprintf( buf, buflen, "NET - Could not listen on the socket" );
if( use_ret == -(POLARSSL_ERR_NET_ACCEPT_FAILED) )
snprintf( buf, buflen, "NET - Could not accept the incoming connection" );
if( use_ret == -(POLARSSL_ERR_NET_RECV_FAILED) )
snprintf( buf, buflen, "NET - Reading information from the socket failed" );
if( use_ret == -(POLARSSL_ERR_NET_SEND_FAILED) )
snprintf( buf, buflen, "NET - Sending information through the socket failed" );
if( use_ret == -(POLARSSL_ERR_NET_CONN_RESET) )
snprintf( buf, buflen, "NET - Connection was reset by peer" );
if( use_ret == -(POLARSSL_ERR_NET_WANT_READ) )
snprintf( buf, buflen, "NET - Connection requires a read call" );
if( use_ret == -(POLARSSL_ERR_NET_WANT_WRITE) )
snprintf( buf, buflen, "NET - Connection requires a write call" );
#endif /* POLARSSL_NET_C */
#if defined(POLARSSL_PADLOCK_C)
if( use_ret == -(POLARSSL_ERR_PADLOCK_DATA_MISALIGNED) )
snprintf( buf, buflen, "PADLOCK - Input data should be aligned" );
#endif /* POLARSSL_PADLOCK_C */
#if defined(POLARSSL_PBKDF2_C)
if( use_ret == -(POLARSSL_ERR_PBKDF2_BAD_INPUT_DATA) )
snprintf( buf, buflen, "PBKDF2 - Bad input parameters to function" );
#endif /* POLARSSL_PBKDF2_C */
#if defined(POLARSSL_SHA1_C)
if( use_ret == -(POLARSSL_ERR_SHA1_FILE_IO_ERROR) )
snprintf( buf, buflen, "SHA1 - Read/write error in file" );
#endif /* POLARSSL_SHA1_C */
#if defined(POLARSSL_SHA2_C)
if( use_ret == -(POLARSSL_ERR_SHA2_FILE_IO_ERROR) )
snprintf( buf, buflen, "SHA2 - Read/write error in file" );
#endif /* POLARSSL_SHA2_C */
#if defined(POLARSSL_SHA4_C)
if( use_ret == -(POLARSSL_ERR_SHA4_FILE_IO_ERROR) )
snprintf( buf, buflen, "SHA4 - Read/write error in file" );
#endif /* POLARSSL_SHA4_C */
#if defined(POLARSSL_XTEA_C)
if( use_ret == -(POLARSSL_ERR_XTEA_INVALID_INPUT_LENGTH) )
snprintf( buf, buflen, "XTEA - The data input has an invalid length" );
#endif /* POLARSSL_XTEA_C */
if( strlen( buf ) != 0 )
return;
snprintf( buf, buflen, "UNKNOWN ERROR CODE (%04X)", use_ret );
}
#else /* POLARSSL_ERROR_C */
#if defined(POLARSSL_ERROR_STRERROR_DUMMY)
#include <string.h>
/*
* Provide an non-function in case POLARSSL_ERROR_C is not defined
*/
void error_strerror( int ret, char *buf, size_t buflen )
{
((void) ret);
if( buflen > 0 )
buf[0] = '\0';
}
#endif /* POLARSSL_ERROR_STRERROR_DUMMY */
#endif /* POLARSSL_ERROR_C */
-621
View File
@@ -1,621 +0,0 @@
/*
* NIST SP800-38D compliant GCM implementation
*
* Copyright (C) 2006-2012, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*
* http://csrc.nist.gov/publications/nistpubs/800-38D/SP-800-38D.pdf
*/
#include "polarssl/config.h"
#if defined(POLARSSL_GCM_C)
#include "polarssl/gcm.h"
/*
* 32-bit integer manipulation macros (big endian)
*/
#ifndef GET_UINT32_BE
#define GET_UINT32_BE(n,b,i) \
{ \
(n) = ( (uint32_t) (b)[(i) ] << 24 ) \
| ( (uint32_t) (b)[(i) + 1] << 16 ) \
| ( (uint32_t) (b)[(i) + 2] << 8 ) \
| ( (uint32_t) (b)[(i) + 3] ); \
}
#endif
#ifndef PUT_UINT32_BE
#define PUT_UINT32_BE(n,b,i) \
{ \
(b)[(i) ] = (unsigned char) ( (n) >> 24 ); \
(b)[(i) + 1] = (unsigned char) ( (n) >> 16 ); \
(b)[(i) + 2] = (unsigned char) ( (n) >> 8 ); \
(b)[(i) + 3] = (unsigned char) ( (n) ); \
}
#endif
static void gcm_gen_table( gcm_context *ctx )
{
int i, j;
uint64_t hi, lo;
uint64_t vl, vh;
unsigned char h[16];
memset( h, 0, 16 );
aes_crypt_ecb( &ctx->aes_ctx, AES_ENCRYPT, h, h );
ctx->HH[0] = 0;
ctx->HL[0] = 0;
GET_UINT32_BE( hi, h, 0 );
GET_UINT32_BE( lo, h, 4 );
vh = (uint64_t) hi << 32 | lo;
GET_UINT32_BE( hi, h, 8 );
GET_UINT32_BE( lo, h, 12 );
vl = (uint64_t) hi << 32 | lo;
ctx->HL[8] = vl;
ctx->HH[8] = vh;
for( i = 4; i > 0; i >>= 1 )
{
uint32_t T = ( vl & 1 ) * 0xe1000000U;
vl = ( vh << 63 ) | ( vl >> 1 );
vh = ( vh >> 1 ) ^ ( (uint64_t) T << 32);
ctx->HL[i] = vl;
ctx->HH[i] = vh;
}
for (i = 2; i < 16; i <<= 1 )
{
uint64_t *HiL = ctx->HL + i, *HiH = ctx->HH + i;
vh = *HiH;
vl = *HiL;
for( j = 1; j < i; j++ )
{
HiH[j] = vh ^ ctx->HH[j];
HiL[j] = vl ^ ctx->HL[j];
}
}
}
int gcm_init( gcm_context *ctx, const unsigned char *key, unsigned int keysize )
{
int ret;
memset( ctx, 0, sizeof(gcm_context) );
if( ( ret = aes_setkey_enc( &ctx->aes_ctx, key, keysize ) ) != 0 )
return( ret );
gcm_gen_table( ctx );
return( 0 );
}
static const uint64_t last4[16] =
{
0x0000, 0x1c20, 0x3840, 0x2460,
0x7080, 0x6ca0, 0x48c0, 0x54e0,
0xe100, 0xfd20, 0xd940, 0xc560,
0x9180, 0x8da0, 0xa9c0, 0xb5e0
};
void gcm_mult( gcm_context *ctx, const unsigned char x[16], unsigned char output[16] )
{
int i = 0;
unsigned char z[16];
unsigned char lo, hi, rem;
uint64_t zh, zl;
memset( z, 0x00, 16 );
lo = x[15] & 0xf;
hi = x[15] >> 4;
zh = ctx->HH[lo];
zl = ctx->HL[lo];
for( i = 15; i >= 0; i-- )
{
lo = x[i] & 0xf;
hi = x[i] >> 4;
if( i != 15 )
{
rem = (unsigned char) zl & 0xf;
zl = ( zh << 60 ) | ( zl >> 4 );
zh = ( zh >> 4 );
zh ^= (uint64_t) last4[rem] << 48;
zh ^= ctx->HH[lo];
zl ^= ctx->HL[lo];
}
rem = (unsigned char) zl & 0xf;
zl = ( zh << 60 ) | ( zl >> 4 );
zh = ( zh >> 4 );
zh ^= (uint64_t) last4[rem] << 48;
zh ^= ctx->HH[hi];
zl ^= ctx->HL[hi];
}
PUT_UINT32_BE( zh >> 32, output, 0 );
PUT_UINT32_BE( zh, output, 4 );
PUT_UINT32_BE( zl >> 32, output, 8 );
PUT_UINT32_BE( zl, output, 12 );
}
int gcm_crypt_and_tag( gcm_context *ctx,
int mode,
size_t length,
const unsigned char *iv,
size_t iv_len,
const unsigned char *add,
size_t add_len,
const unsigned char *input,
unsigned char *output,
size_t tag_len,
unsigned char *tag )
{
unsigned char y[16];
unsigned char ectr[16];
unsigned char buf[16];
unsigned char work_buf[16];
size_t i;
const unsigned char *p;
unsigned char *out_p = output;
size_t use_len;
uint64_t orig_len = length * 8;
uint64_t orig_add_len = add_len * 8;
memset( y, 0x00, 16 );
memset( work_buf, 0x00, 16 );
memset( tag, 0x00, tag_len );
memset( buf, 0x00, 16 );
if( ( mode == GCM_DECRYPT && output <= input && ( input - output ) < 8 ) ||
( output > input && (size_t) ( output - input ) < length ) )
{
return( POLARSSL_ERR_GCM_BAD_INPUT );
}
if( iv_len == 12 )
{
memcpy( y, iv, iv_len );
y[15] = 1;
}
else
{
memset( work_buf, 0x00, 16 );
PUT_UINT32_BE( iv_len * 8, work_buf, 12 );
p = iv;
while( iv_len > 0 )
{
use_len = ( iv_len < 16 ) ? iv_len : 16;
for( i = 0; i < use_len; i++ )
y[i] ^= p[i];
gcm_mult( ctx, y, y );
iv_len -= use_len;
p += use_len;
}
for( i = 0; i < 16; i++ )
y[i] ^= work_buf[i];
gcm_mult( ctx, y, y );
}
aes_crypt_ecb( &ctx->aes_ctx, AES_ENCRYPT, y, ectr );
memcpy( tag, ectr, tag_len );
p = add;
while( add_len > 0 )
{
use_len = ( add_len < 16 ) ? add_len : 16;
for( i = 0; i < use_len; i++ )
buf[i] ^= p[i];
gcm_mult( ctx, buf, buf );
add_len -= use_len;
p += use_len;
}
p = input;
while( length > 0 )
{
use_len = ( length < 16 ) ? length : 16;
for( i = 16; i > 12; i-- )
if( ++y[i - 1] != 0 )
break;
aes_crypt_ecb( &ctx->aes_ctx, AES_ENCRYPT, y, ectr );
for( i = 0; i < use_len; i++ )
{
out_p[i] = ectr[i] ^ p[i];
if( mode == GCM_ENCRYPT )
buf[i] ^= out_p[i];
else
buf[i] ^= p[i];
}
gcm_mult( ctx, buf, buf );
length -= use_len;
p += use_len;
out_p += use_len;
}
if( orig_len || orig_add_len )
{
memset( work_buf, 0x00, 16 );
PUT_UINT32_BE( ( orig_add_len >> 32 ), work_buf, 0 );
PUT_UINT32_BE( ( orig_add_len ), work_buf, 4 );
PUT_UINT32_BE( ( orig_len >> 32 ), work_buf, 8 );
PUT_UINT32_BE( ( orig_len ), work_buf, 12 );
for( i = 0; i < 16; i++ )
buf[i] ^= work_buf[i];
gcm_mult( ctx, buf, buf );
for( i = 0; i < tag_len; i++ )
tag[i] ^= buf[i];
}
return( 0 );
}
int gcm_auth_decrypt( gcm_context *ctx,
size_t length,
const unsigned char *iv,
size_t iv_len,
const unsigned char *add,
size_t add_len,
const unsigned char *tag,
size_t tag_len,
const unsigned char *input,
unsigned char *output )
{
unsigned char check_tag[16];
gcm_crypt_and_tag( ctx, GCM_DECRYPT, length, iv, iv_len, add, add_len, input, output, tag_len, check_tag );
if( memcmp( check_tag, tag, tag_len ) == 0 )
return( 0 );
memset( output, 0, length );
return( POLARSSL_ERR_GCM_AUTH_FAILED );
}
#if defined(POLARSSL_SELF_TEST)
#include <stdio.h>
/*
* GCM test vectors from:
*
* http://csrc.nist.gov/groups/STM/cavp/documents/mac/gcmtestvectors.zip
*/
#define MAX_TESTS 6
int key_index[MAX_TESTS] =
{ 0, 0, 1, 1, 1, 1 };
unsigned char key[MAX_TESTS][32] =
{
{ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
{ 0xfe, 0xff, 0xe9, 0x92, 0x86, 0x65, 0x73, 0x1c,
0x6d, 0x6a, 0x8f, 0x94, 0x67, 0x30, 0x83, 0x08,
0xfe, 0xff, 0xe9, 0x92, 0x86, 0x65, 0x73, 0x1c,
0x6d, 0x6a, 0x8f, 0x94, 0x67, 0x30, 0x83, 0x08 },
};
size_t iv_len[MAX_TESTS] =
{ 12, 12, 12, 12, 8, 60 };
int iv_index[MAX_TESTS] =
{ 0, 0, 1, 1, 1, 2 };
unsigned char iv[MAX_TESTS][64] =
{
{ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00 },
{ 0xca, 0xfe, 0xba, 0xbe, 0xfa, 0xce, 0xdb, 0xad,
0xde, 0xca, 0xf8, 0x88 },
{ 0x93, 0x13, 0x22, 0x5d, 0xf8, 0x84, 0x06, 0xe5,
0x55, 0x90, 0x9c, 0x5a, 0xff, 0x52, 0x69, 0xaa,
0x6a, 0x7a, 0x95, 0x38, 0x53, 0x4f, 0x7d, 0xa1,
0xe4, 0xc3, 0x03, 0xd2, 0xa3, 0x18, 0xa7, 0x28,
0xc3, 0xc0, 0xc9, 0x51, 0x56, 0x80, 0x95, 0x39,
0xfc, 0xf0, 0xe2, 0x42, 0x9a, 0x6b, 0x52, 0x54,
0x16, 0xae, 0xdb, 0xf5, 0xa0, 0xde, 0x6a, 0x57,
0xa6, 0x37, 0xb3, 0x9b },
};
size_t add_len[MAX_TESTS] =
{ 0, 0, 0, 20, 20, 20 };
int add_index[MAX_TESTS] =
{ 0, 0, 0, 1, 1, 1 };
unsigned char additional[MAX_TESTS][64] =
{
{ 0x00 },
{ 0xfe, 0xed, 0xfa, 0xce, 0xde, 0xad, 0xbe, 0xef,
0xfe, 0xed, 0xfa, 0xce, 0xde, 0xad, 0xbe, 0xef,
0xab, 0xad, 0xda, 0xd2 },
};
size_t pt_len[MAX_TESTS] =
{ 0, 16, 64, 60, 60, 60 };
int pt_index[MAX_TESTS] =
{ 0, 0, 1, 1, 1, 1 };
unsigned char pt[MAX_TESTS][64] =
{
{ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
{ 0xd9, 0x31, 0x32, 0x25, 0xf8, 0x84, 0x06, 0xe5,
0xa5, 0x59, 0x09, 0xc5, 0xaf, 0xf5, 0x26, 0x9a,
0x86, 0xa7, 0xa9, 0x53, 0x15, 0x34, 0xf7, 0xda,
0x2e, 0x4c, 0x30, 0x3d, 0x8a, 0x31, 0x8a, 0x72,
0x1c, 0x3c, 0x0c, 0x95, 0x95, 0x68, 0x09, 0x53,
0x2f, 0xcf, 0x0e, 0x24, 0x49, 0xa6, 0xb5, 0x25,
0xb1, 0x6a, 0xed, 0xf5, 0xaa, 0x0d, 0xe6, 0x57,
0xba, 0x63, 0x7b, 0x39, 0x1a, 0xaf, 0xd2, 0x55 },
};
unsigned char ct[MAX_TESTS * 3][64] =
{
{ 0x00 },
{ 0x03, 0x88, 0xda, 0xce, 0x60, 0xb6, 0xa3, 0x92,
0xf3, 0x28, 0xc2, 0xb9, 0x71, 0xb2, 0xfe, 0x78 },
{ 0x42, 0x83, 0x1e, 0xc2, 0x21, 0x77, 0x74, 0x24,
0x4b, 0x72, 0x21, 0xb7, 0x84, 0xd0, 0xd4, 0x9c,
0xe3, 0xaa, 0x21, 0x2f, 0x2c, 0x02, 0xa4, 0xe0,
0x35, 0xc1, 0x7e, 0x23, 0x29, 0xac, 0xa1, 0x2e,
0x21, 0xd5, 0x14, 0xb2, 0x54, 0x66, 0x93, 0x1c,
0x7d, 0x8f, 0x6a, 0x5a, 0xac, 0x84, 0xaa, 0x05,
0x1b, 0xa3, 0x0b, 0x39, 0x6a, 0x0a, 0xac, 0x97,
0x3d, 0x58, 0xe0, 0x91, 0x47, 0x3f, 0x59, 0x85 },
{ 0x42, 0x83, 0x1e, 0xc2, 0x21, 0x77, 0x74, 0x24,
0x4b, 0x72, 0x21, 0xb7, 0x84, 0xd0, 0xd4, 0x9c,
0xe3, 0xaa, 0x21, 0x2f, 0x2c, 0x02, 0xa4, 0xe0,
0x35, 0xc1, 0x7e, 0x23, 0x29, 0xac, 0xa1, 0x2e,
0x21, 0xd5, 0x14, 0xb2, 0x54, 0x66, 0x93, 0x1c,
0x7d, 0x8f, 0x6a, 0x5a, 0xac, 0x84, 0xaa, 0x05,
0x1b, 0xa3, 0x0b, 0x39, 0x6a, 0x0a, 0xac, 0x97,
0x3d, 0x58, 0xe0, 0x91 },
{ 0x61, 0x35, 0x3b, 0x4c, 0x28, 0x06, 0x93, 0x4a,
0x77, 0x7f, 0xf5, 0x1f, 0xa2, 0x2a, 0x47, 0x55,
0x69, 0x9b, 0x2a, 0x71, 0x4f, 0xcd, 0xc6, 0xf8,
0x37, 0x66, 0xe5, 0xf9, 0x7b, 0x6c, 0x74, 0x23,
0x73, 0x80, 0x69, 0x00, 0xe4, 0x9f, 0x24, 0xb2,
0x2b, 0x09, 0x75, 0x44, 0xd4, 0x89, 0x6b, 0x42,
0x49, 0x89, 0xb5, 0xe1, 0xeb, 0xac, 0x0f, 0x07,
0xc2, 0x3f, 0x45, 0x98 },
{ 0x8c, 0xe2, 0x49, 0x98, 0x62, 0x56, 0x15, 0xb6,
0x03, 0xa0, 0x33, 0xac, 0xa1, 0x3f, 0xb8, 0x94,
0xbe, 0x91, 0x12, 0xa5, 0xc3, 0xa2, 0x11, 0xa8,
0xba, 0x26, 0x2a, 0x3c, 0xca, 0x7e, 0x2c, 0xa7,
0x01, 0xe4, 0xa9, 0xa4, 0xfb, 0xa4, 0x3c, 0x90,
0xcc, 0xdc, 0xb2, 0x81, 0xd4, 0x8c, 0x7c, 0x6f,
0xd6, 0x28, 0x75, 0xd2, 0xac, 0xa4, 0x17, 0x03,
0x4c, 0x34, 0xae, 0xe5 },
{ 0x00 },
{ 0x98, 0xe7, 0x24, 0x7c, 0x07, 0xf0, 0xfe, 0x41,
0x1c, 0x26, 0x7e, 0x43, 0x84, 0xb0, 0xf6, 0x00 },
{ 0x39, 0x80, 0xca, 0x0b, 0x3c, 0x00, 0xe8, 0x41,
0xeb, 0x06, 0xfa, 0xc4, 0x87, 0x2a, 0x27, 0x57,
0x85, 0x9e, 0x1c, 0xea, 0xa6, 0xef, 0xd9, 0x84,
0x62, 0x85, 0x93, 0xb4, 0x0c, 0xa1, 0xe1, 0x9c,
0x7d, 0x77, 0x3d, 0x00, 0xc1, 0x44, 0xc5, 0x25,
0xac, 0x61, 0x9d, 0x18, 0xc8, 0x4a, 0x3f, 0x47,
0x18, 0xe2, 0x44, 0x8b, 0x2f, 0xe3, 0x24, 0xd9,
0xcc, 0xda, 0x27, 0x10, 0xac, 0xad, 0xe2, 0x56 },
{ 0x39, 0x80, 0xca, 0x0b, 0x3c, 0x00, 0xe8, 0x41,
0xeb, 0x06, 0xfa, 0xc4, 0x87, 0x2a, 0x27, 0x57,
0x85, 0x9e, 0x1c, 0xea, 0xa6, 0xef, 0xd9, 0x84,
0x62, 0x85, 0x93, 0xb4, 0x0c, 0xa1, 0xe1, 0x9c,
0x7d, 0x77, 0x3d, 0x00, 0xc1, 0x44, 0xc5, 0x25,
0xac, 0x61, 0x9d, 0x18, 0xc8, 0x4a, 0x3f, 0x47,
0x18, 0xe2, 0x44, 0x8b, 0x2f, 0xe3, 0x24, 0xd9,
0xcc, 0xda, 0x27, 0x10 },
{ 0x0f, 0x10, 0xf5, 0x99, 0xae, 0x14, 0xa1, 0x54,
0xed, 0x24, 0xb3, 0x6e, 0x25, 0x32, 0x4d, 0xb8,
0xc5, 0x66, 0x63, 0x2e, 0xf2, 0xbb, 0xb3, 0x4f,
0x83, 0x47, 0x28, 0x0f, 0xc4, 0x50, 0x70, 0x57,
0xfd, 0xdc, 0x29, 0xdf, 0x9a, 0x47, 0x1f, 0x75,
0xc6, 0x65, 0x41, 0xd4, 0xd4, 0xda, 0xd1, 0xc9,
0xe9, 0x3a, 0x19, 0xa5, 0x8e, 0x8b, 0x47, 0x3f,
0xa0, 0xf0, 0x62, 0xf7 },
{ 0xd2, 0x7e, 0x88, 0x68, 0x1c, 0xe3, 0x24, 0x3c,
0x48, 0x30, 0x16, 0x5a, 0x8f, 0xdc, 0xf9, 0xff,
0x1d, 0xe9, 0xa1, 0xd8, 0xe6, 0xb4, 0x47, 0xef,
0x6e, 0xf7, 0xb7, 0x98, 0x28, 0x66, 0x6e, 0x45,
0x81, 0xe7, 0x90, 0x12, 0xaf, 0x34, 0xdd, 0xd9,
0xe2, 0xf0, 0x37, 0x58, 0x9b, 0x29, 0x2d, 0xb3,
0xe6, 0x7c, 0x03, 0x67, 0x45, 0xfa, 0x22, 0xe7,
0xe9, 0xb7, 0x37, 0x3b },
{ 0x00 },
{ 0xce, 0xa7, 0x40, 0x3d, 0x4d, 0x60, 0x6b, 0x6e,
0x07, 0x4e, 0xc5, 0xd3, 0xba, 0xf3, 0x9d, 0x18 },
{ 0x52, 0x2d, 0xc1, 0xf0, 0x99, 0x56, 0x7d, 0x07,
0xf4, 0x7f, 0x37, 0xa3, 0x2a, 0x84, 0x42, 0x7d,
0x64, 0x3a, 0x8c, 0xdc, 0xbf, 0xe5, 0xc0, 0xc9,
0x75, 0x98, 0xa2, 0xbd, 0x25, 0x55, 0xd1, 0xaa,
0x8c, 0xb0, 0x8e, 0x48, 0x59, 0x0d, 0xbb, 0x3d,
0xa7, 0xb0, 0x8b, 0x10, 0x56, 0x82, 0x88, 0x38,
0xc5, 0xf6, 0x1e, 0x63, 0x93, 0xba, 0x7a, 0x0a,
0xbc, 0xc9, 0xf6, 0x62, 0x89, 0x80, 0x15, 0xad },
{ 0x52, 0x2d, 0xc1, 0xf0, 0x99, 0x56, 0x7d, 0x07,
0xf4, 0x7f, 0x37, 0xa3, 0x2a, 0x84, 0x42, 0x7d,
0x64, 0x3a, 0x8c, 0xdc, 0xbf, 0xe5, 0xc0, 0xc9,
0x75, 0x98, 0xa2, 0xbd, 0x25, 0x55, 0xd1, 0xaa,
0x8c, 0xb0, 0x8e, 0x48, 0x59, 0x0d, 0xbb, 0x3d,
0xa7, 0xb0, 0x8b, 0x10, 0x56, 0x82, 0x88, 0x38,
0xc5, 0xf6, 0x1e, 0x63, 0x93, 0xba, 0x7a, 0x0a,
0xbc, 0xc9, 0xf6, 0x62 },
{ 0xc3, 0x76, 0x2d, 0xf1, 0xca, 0x78, 0x7d, 0x32,
0xae, 0x47, 0xc1, 0x3b, 0xf1, 0x98, 0x44, 0xcb,
0xaf, 0x1a, 0xe1, 0x4d, 0x0b, 0x97, 0x6a, 0xfa,
0xc5, 0x2f, 0xf7, 0xd7, 0x9b, 0xba, 0x9d, 0xe0,
0xfe, 0xb5, 0x82, 0xd3, 0x39, 0x34, 0xa4, 0xf0,
0x95, 0x4c, 0xc2, 0x36, 0x3b, 0xc7, 0x3f, 0x78,
0x62, 0xac, 0x43, 0x0e, 0x64, 0xab, 0xe4, 0x99,
0xf4, 0x7c, 0x9b, 0x1f },
{ 0x5a, 0x8d, 0xef, 0x2f, 0x0c, 0x9e, 0x53, 0xf1,
0xf7, 0x5d, 0x78, 0x53, 0x65, 0x9e, 0x2a, 0x20,
0xee, 0xb2, 0xb2, 0x2a, 0xaf, 0xde, 0x64, 0x19,
0xa0, 0x58, 0xab, 0x4f, 0x6f, 0x74, 0x6b, 0xf4,
0x0f, 0xc0, 0xc3, 0xb7, 0x80, 0xf2, 0x44, 0x45,
0x2d, 0xa3, 0xeb, 0xf1, 0xc5, 0xd8, 0x2c, 0xde,
0xa2, 0x41, 0x89, 0x97, 0x20, 0x0e, 0xf8, 0x2e,
0x44, 0xae, 0x7e, 0x3f },
};
unsigned char tag[MAX_TESTS * 3][16] =
{
{ 0x58, 0xe2, 0xfc, 0xce, 0xfa, 0x7e, 0x30, 0x61,
0x36, 0x7f, 0x1d, 0x57, 0xa4, 0xe7, 0x45, 0x5a },
{ 0xab, 0x6e, 0x47, 0xd4, 0x2c, 0xec, 0x13, 0xbd,
0xf5, 0x3a, 0x67, 0xb2, 0x12, 0x57, 0xbd, 0xdf },
{ 0x4d, 0x5c, 0x2a, 0xf3, 0x27, 0xcd, 0x64, 0xa6,
0x2c, 0xf3, 0x5a, 0xbd, 0x2b, 0xa6, 0xfa, 0xb4 },
{ 0x5b, 0xc9, 0x4f, 0xbc, 0x32, 0x21, 0xa5, 0xdb,
0x94, 0xfa, 0xe9, 0x5a, 0xe7, 0x12, 0x1a, 0x47 },
{ 0x36, 0x12, 0xd2, 0xe7, 0x9e, 0x3b, 0x07, 0x85,
0x56, 0x1b, 0xe1, 0x4a, 0xac, 0xa2, 0xfc, 0xcb },
{ 0x61, 0x9c, 0xc5, 0xae, 0xff, 0xfe, 0x0b, 0xfa,
0x46, 0x2a, 0xf4, 0x3c, 0x16, 0x99, 0xd0, 0x50 },
{ 0xcd, 0x33, 0xb2, 0x8a, 0xc7, 0x73, 0xf7, 0x4b,
0xa0, 0x0e, 0xd1, 0xf3, 0x12, 0x57, 0x24, 0x35 },
{ 0x2f, 0xf5, 0x8d, 0x80, 0x03, 0x39, 0x27, 0xab,
0x8e, 0xf4, 0xd4, 0x58, 0x75, 0x14, 0xf0, 0xfb },
{ 0x99, 0x24, 0xa7, 0xc8, 0x58, 0x73, 0x36, 0xbf,
0xb1, 0x18, 0x02, 0x4d, 0xb8, 0x67, 0x4a, 0x14 },
{ 0x25, 0x19, 0x49, 0x8e, 0x80, 0xf1, 0x47, 0x8f,
0x37, 0xba, 0x55, 0xbd, 0x6d, 0x27, 0x61, 0x8c },
{ 0x65, 0xdc, 0xc5, 0x7f, 0xcf, 0x62, 0x3a, 0x24,
0x09, 0x4f, 0xcc, 0xa4, 0x0d, 0x35, 0x33, 0xf8 },
{ 0xdc, 0xf5, 0x66, 0xff, 0x29, 0x1c, 0x25, 0xbb,
0xb8, 0x56, 0x8f, 0xc3, 0xd3, 0x76, 0xa6, 0xd9 },
{ 0x53, 0x0f, 0x8a, 0xfb, 0xc7, 0x45, 0x36, 0xb9,
0xa9, 0x63, 0xb4, 0xf1, 0xc4, 0xcb, 0x73, 0x8b },
{ 0xd0, 0xd1, 0xc8, 0xa7, 0x99, 0x99, 0x6b, 0xf0,
0x26, 0x5b, 0x98, 0xb5, 0xd4, 0x8a, 0xb9, 0x19 },
{ 0xb0, 0x94, 0xda, 0xc5, 0xd9, 0x34, 0x71, 0xbd,
0xec, 0x1a, 0x50, 0x22, 0x70, 0xe3, 0xcc, 0x6c },
{ 0x76, 0xfc, 0x6e, 0xce, 0x0f, 0x4e, 0x17, 0x68,
0xcd, 0xdf, 0x88, 0x53, 0xbb, 0x2d, 0x55, 0x1b },
{ 0x3a, 0x33, 0x7d, 0xbf, 0x46, 0xa7, 0x92, 0xc4,
0x5e, 0x45, 0x49, 0x13, 0xfe, 0x2e, 0xa8, 0xf2 },
{ 0xa4, 0x4a, 0x82, 0x66, 0xee, 0x1c, 0x8e, 0xb0,
0xc8, 0xb5, 0xd4, 0xcf, 0x5a, 0xe9, 0xf1, 0x9a },
};
int gcm_self_test( int verbose )
{
gcm_context ctx;
unsigned char buf[64];
unsigned char tag_buf[16];
int i, j, ret;
for( j = 0; j < 3; j++ )
{
int key_len = 128 + 64 * j;
for( i = 0; i < MAX_TESTS; i++ )
{
printf( " AES-GCM-%3d #%d (%s): ", key_len, i, "enc" );
gcm_init( &ctx, key[key_index[i]], key_len );
ret = gcm_crypt_and_tag( &ctx, GCM_ENCRYPT,
pt_len[i],
iv[iv_index[i]], iv_len[i],
additional[add_index[i]], add_len[i],
pt[pt_index[i]], buf, 16, tag_buf );
if( ret != 0 ||
memcmp( buf, ct[j * 6 + i], pt_len[i] ) != 0 ||
memcmp( tag_buf, tag[j * 6 + i], 16 ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( verbose != 0 )
printf( "passed\n" );
printf( " AES-GCM-%3d #%d (%s): ", key_len, i, "dec" );
gcm_init( &ctx, key[key_index[i]], key_len );
ret = gcm_crypt_and_tag( &ctx, GCM_DECRYPT,
pt_len[i],
iv[iv_index[i]], iv_len[i],
additional[add_index[i]], add_len[i],
ct[j * 6 + i], buf, 16, tag_buf );
if( ret != 0 ||
memcmp( buf, pt[pt_index[i]], pt_len[i] ) != 0 ||
memcmp( tag_buf, tag[j * 6 + i], 16 ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( verbose != 0 )
printf( "passed\n" );
}
}
printf( "\n" );
return( 0 );
}
#endif
#endif
-231
View File
@@ -1,231 +0,0 @@
/**
* \brief HAVEGE: HArdware Volatile Entropy Gathering and Expansion
*
* Copyright (C) 2006-2010, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*
* The HAVEGE RNG was designed by Andre Seznec in 2002.
*
* http://www.irisa.fr/caps/projects/hipsor/publi.php
*
* Contact: seznec(at)irisa_dot_fr - orocheco(at)irisa_dot_fr
*/
#include "polarssl/config.h"
#if defined(POLARSSL_HAVEGE_C)
#include "polarssl/havege.h"
#include "polarssl/timing.h"
#include <string.h>
#include <time.h>
/* ------------------------------------------------------------------------
* On average, one iteration accesses two 8-word blocks in the havege WALK
* table, and generates 16 words in the RES array.
*
* The data read in the WALK table is updated and permuted after each use.
* The result of the hardware clock counter read is used for this update.
*
* 25 conditional tests are present. The conditional tests are grouped in
* two nested groups of 12 conditional tests and 1 test that controls the
* permutation; on average, there should be 6 tests executed and 3 of them
* should be mispredicted.
* ------------------------------------------------------------------------
*/
#define SWAP(X,Y) { int *T = X; X = Y; Y = T; }
#define TST1_ENTER if( PTEST & 1 ) { PTEST ^= 3; PTEST >>= 1;
#define TST2_ENTER if( PTEST & 1 ) { PTEST ^= 3; PTEST >>= 1;
#define TST1_LEAVE U1++; }
#define TST2_LEAVE U2++; }
#define ONE_ITERATION \
\
PTEST = PT1 >> 20; \
\
TST1_ENTER TST1_ENTER TST1_ENTER TST1_ENTER \
TST1_ENTER TST1_ENTER TST1_ENTER TST1_ENTER \
TST1_ENTER TST1_ENTER TST1_ENTER TST1_ENTER \
\
TST1_LEAVE TST1_LEAVE TST1_LEAVE TST1_LEAVE \
TST1_LEAVE TST1_LEAVE TST1_LEAVE TST1_LEAVE \
TST1_LEAVE TST1_LEAVE TST1_LEAVE TST1_LEAVE \
\
PTX = (PT1 >> 18) & 7; \
PT1 &= 0x1FFF; \
PT2 &= 0x1FFF; \
CLK = (int) hardclock(); \
\
i = 0; \
A = &WALK[PT1 ]; RES[i++] ^= *A; \
B = &WALK[PT2 ]; RES[i++] ^= *B; \
C = &WALK[PT1 ^ 1]; RES[i++] ^= *C; \
D = &WALK[PT2 ^ 4]; RES[i++] ^= *D; \
\
IN = (*A >> (1)) ^ (*A << (31)) ^ CLK; \
*A = (*B >> (2)) ^ (*B << (30)) ^ CLK; \
*B = IN ^ U1; \
*C = (*C >> (3)) ^ (*C << (29)) ^ CLK; \
*D = (*D >> (4)) ^ (*D << (28)) ^ CLK; \
\
A = &WALK[PT1 ^ 2]; RES[i++] ^= *A; \
B = &WALK[PT2 ^ 2]; RES[i++] ^= *B; \
C = &WALK[PT1 ^ 3]; RES[i++] ^= *C; \
D = &WALK[PT2 ^ 6]; RES[i++] ^= *D; \
\
if( PTEST & 1 ) SWAP( A, C ); \
\
IN = (*A >> (5)) ^ (*A << (27)) ^ CLK; \
*A = (*B >> (6)) ^ (*B << (26)) ^ CLK; \
*B = IN; CLK = (int) hardclock(); \
*C = (*C >> (7)) ^ (*C << (25)) ^ CLK; \
*D = (*D >> (8)) ^ (*D << (24)) ^ CLK; \
\
A = &WALK[PT1 ^ 4]; \
B = &WALK[PT2 ^ 1]; \
\
PTEST = PT2 >> 1; \
\
PT2 = (RES[(i - 8) ^ PTY] ^ WALK[PT2 ^ PTY ^ 7]); \
PT2 = ((PT2 & 0x1FFF) & (~8)) ^ ((PT1 ^ 8) & 0x8); \
PTY = (PT2 >> 10) & 7; \
\
TST2_ENTER TST2_ENTER TST2_ENTER TST2_ENTER \
TST2_ENTER TST2_ENTER TST2_ENTER TST2_ENTER \
TST2_ENTER TST2_ENTER TST2_ENTER TST2_ENTER \
\
TST2_LEAVE TST2_LEAVE TST2_LEAVE TST2_LEAVE \
TST2_LEAVE TST2_LEAVE TST2_LEAVE TST2_LEAVE \
TST2_LEAVE TST2_LEAVE TST2_LEAVE TST2_LEAVE \
\
C = &WALK[PT1 ^ 5]; \
D = &WALK[PT2 ^ 5]; \
\
RES[i++] ^= *A; \
RES[i++] ^= *B; \
RES[i++] ^= *C; \
RES[i++] ^= *D; \
\
IN = (*A >> ( 9)) ^ (*A << (23)) ^ CLK; \
*A = (*B >> (10)) ^ (*B << (22)) ^ CLK; \
*B = IN ^ U2; \
*C = (*C >> (11)) ^ (*C << (21)) ^ CLK; \
*D = (*D >> (12)) ^ (*D << (20)) ^ CLK; \
\
A = &WALK[PT1 ^ 6]; RES[i++] ^= *A; \
B = &WALK[PT2 ^ 3]; RES[i++] ^= *B; \
C = &WALK[PT1 ^ 7]; RES[i++] ^= *C; \
D = &WALK[PT2 ^ 7]; RES[i++] ^= *D; \
\
IN = (*A >> (13)) ^ (*A << (19)) ^ CLK; \
*A = (*B >> (14)) ^ (*B << (18)) ^ CLK; \
*B = IN; \
*C = (*C >> (15)) ^ (*C << (17)) ^ CLK; \
*D = (*D >> (16)) ^ (*D << (16)) ^ CLK; \
\
PT1 = ( RES[(i - 8) ^ PTX] ^ \
WALK[PT1 ^ PTX ^ 7] ) & (~1); \
PT1 ^= (PT2 ^ 0x10) & 0x10; \
\
for( n++, i = 0; i < 16; i++ ) \
hs->pool[n % COLLECT_SIZE] ^= RES[i];
/*
* Entropy gathering function
*/
static void havege_fill( havege_state *hs )
{
int i, n = 0;
int U1, U2, *A, *B, *C, *D;
int PT1, PT2, *WALK, RES[16];
int PTX, PTY, CLK, PTEST, IN;
WALK = hs->WALK;
PT1 = hs->PT1;
PT2 = hs->PT2;
PTX = U1 = 0;
PTY = U2 = 0;
memset( RES, 0, sizeof( RES ) );
while( n < COLLECT_SIZE * 4 )
{
ONE_ITERATION
ONE_ITERATION
ONE_ITERATION
ONE_ITERATION
}
hs->PT1 = PT1;
hs->PT2 = PT2;
hs->offset[0] = 0;
hs->offset[1] = COLLECT_SIZE / 2;
}
/*
* HAVEGE initialization
*/
void havege_init( havege_state *hs )
{
memset( hs, 0, sizeof( havege_state ) );
havege_fill( hs );
}
/*
* HAVEGE rand function
*/
int havege_random( void *p_rng, unsigned char *buf, size_t len )
{
int val;
size_t use_len;
havege_state *hs = (havege_state *) p_rng;
unsigned char *p = buf;
while( len > 0 )
{
use_len = len;
if( use_len > sizeof(int) )
use_len = sizeof(int);
if( hs->offset[1] >= COLLECT_SIZE )
havege_fill( hs );
val = hs->pool[hs->offset[0]++];
val ^= hs->pool[hs->offset[1]++];
memcpy( p, &val, use_len );
len -= use_len;
p += use_len;
}
return( 0 );
}
#endif
-368
View File
@@ -1,368 +0,0 @@
/*
* RFC 1115/1319 compliant MD2 implementation
*
* Copyright (C) 2006-2013, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*
* The MD2 algorithm was designed by Ron Rivest in 1989.
*
* http://www.ietf.org/rfc/rfc1115.txt
* http://www.ietf.org/rfc/rfc1319.txt
*/
#include "polarssl/config.h"
#if defined(POLARSSL_MD2_C)
#include "polarssl/md2.h"
#if defined(POLARSSL_FS_IO) || defined(POLARSSL_SELF_TEST)
#include <stdio.h>
#endif
#if !defined(POLARSSL_MD2_ALT)
static const unsigned char PI_SUBST[256] =
{
0x29, 0x2E, 0x43, 0xC9, 0xA2, 0xD8, 0x7C, 0x01, 0x3D, 0x36,
0x54, 0xA1, 0xEC, 0xF0, 0x06, 0x13, 0x62, 0xA7, 0x05, 0xF3,
0xC0, 0xC7, 0x73, 0x8C, 0x98, 0x93, 0x2B, 0xD9, 0xBC, 0x4C,
0x82, 0xCA, 0x1E, 0x9B, 0x57, 0x3C, 0xFD, 0xD4, 0xE0, 0x16,
0x67, 0x42, 0x6F, 0x18, 0x8A, 0x17, 0xE5, 0x12, 0xBE, 0x4E,
0xC4, 0xD6, 0xDA, 0x9E, 0xDE, 0x49, 0xA0, 0xFB, 0xF5, 0x8E,
0xBB, 0x2F, 0xEE, 0x7A, 0xA9, 0x68, 0x79, 0x91, 0x15, 0xB2,
0x07, 0x3F, 0x94, 0xC2, 0x10, 0x89, 0x0B, 0x22, 0x5F, 0x21,
0x80, 0x7F, 0x5D, 0x9A, 0x5A, 0x90, 0x32, 0x27, 0x35, 0x3E,
0xCC, 0xE7, 0xBF, 0xF7, 0x97, 0x03, 0xFF, 0x19, 0x30, 0xB3,
0x48, 0xA5, 0xB5, 0xD1, 0xD7, 0x5E, 0x92, 0x2A, 0xAC, 0x56,
0xAA, 0xC6, 0x4F, 0xB8, 0x38, 0xD2, 0x96, 0xA4, 0x7D, 0xB6,
0x76, 0xFC, 0x6B, 0xE2, 0x9C, 0x74, 0x04, 0xF1, 0x45, 0x9D,
0x70, 0x59, 0x64, 0x71, 0x87, 0x20, 0x86, 0x5B, 0xCF, 0x65,
0xE6, 0x2D, 0xA8, 0x02, 0x1B, 0x60, 0x25, 0xAD, 0xAE, 0xB0,
0xB9, 0xF6, 0x1C, 0x46, 0x61, 0x69, 0x34, 0x40, 0x7E, 0x0F,
0x55, 0x47, 0xA3, 0x23, 0xDD, 0x51, 0xAF, 0x3A, 0xC3, 0x5C,
0xF9, 0xCE, 0xBA, 0xC5, 0xEA, 0x26, 0x2C, 0x53, 0x0D, 0x6E,
0x85, 0x28, 0x84, 0x09, 0xD3, 0xDF, 0xCD, 0xF4, 0x41, 0x81,
0x4D, 0x52, 0x6A, 0xDC, 0x37, 0xC8, 0x6C, 0xC1, 0xAB, 0xFA,
0x24, 0xE1, 0x7B, 0x08, 0x0C, 0xBD, 0xB1, 0x4A, 0x78, 0x88,
0x95, 0x8B, 0xE3, 0x63, 0xE8, 0x6D, 0xE9, 0xCB, 0xD5, 0xFE,
0x3B, 0x00, 0x1D, 0x39, 0xF2, 0xEF, 0xB7, 0x0E, 0x66, 0x58,
0xD0, 0xE4, 0xA6, 0x77, 0x72, 0xF8, 0xEB, 0x75, 0x4B, 0x0A,
0x31, 0x44, 0x50, 0xB4, 0x8F, 0xED, 0x1F, 0x1A, 0xDB, 0x99,
0x8D, 0x33, 0x9F, 0x11, 0x83, 0x14
};
/*
* MD2 context setup
*/
void md2_starts( md2_context *ctx )
{
memset( ctx->cksum, 0, 16 );
memset( ctx->state, 0, 46 );
memset( ctx->buffer, 0, 16 );
ctx->left = 0;
}
static void md2_process( md2_context *ctx )
{
int i, j;
unsigned char t = 0;
for( i = 0; i < 16; i++ )
{
ctx->state[i + 16] = ctx->buffer[i];
ctx->state[i + 32] =
(unsigned char)( ctx->buffer[i] ^ ctx->state[i]);
}
for( i = 0; i < 18; i++ )
{
for( j = 0; j < 48; j++ )
{
ctx->state[j] = (unsigned char)
( ctx->state[j] ^ PI_SUBST[t] );
t = ctx->state[j];
}
t = (unsigned char)( t + i );
}
t = ctx->cksum[15];
for( i = 0; i < 16; i++ )
{
ctx->cksum[i] = (unsigned char)
( ctx->cksum[i] ^ PI_SUBST[ctx->buffer[i] ^ t] );
t = ctx->cksum[i];
}
}
/*
* MD2 process buffer
*/
void md2_update( md2_context *ctx, const unsigned char *input, size_t ilen )
{
size_t fill;
while( ilen > 0 )
{
if( ctx->left + ilen > 16 )
fill = 16 - ctx->left;
else
fill = ilen;
memcpy( ctx->buffer + ctx->left, input, fill );
ctx->left += fill;
input += fill;
ilen -= fill;
if( ctx->left == 16 )
{
ctx->left = 0;
md2_process( ctx );
}
}
}
/*
* MD2 final digest
*/
void md2_finish( md2_context *ctx, unsigned char output[16] )
{
size_t i;
unsigned char x;
x = (unsigned char)( 16 - ctx->left );
for( i = ctx->left; i < 16; i++ )
ctx->buffer[i] = x;
md2_process( ctx );
memcpy( ctx->buffer, ctx->cksum, 16 );
md2_process( ctx );
memcpy( output, ctx->state, 16 );
}
#endif /* !POLARSSL_MD2_ALT */
/*
* output = MD2( input buffer )
*/
void md2( const unsigned char *input, size_t ilen, unsigned char output[16] )
{
md2_context ctx;
md2_starts( &ctx );
md2_update( &ctx, input, ilen );
md2_finish( &ctx, output );
memset( &ctx, 0, sizeof( md2_context ) );
}
#if defined(POLARSSL_FS_IO)
/*
* output = MD2( file contents )
*/
int md2_file( const char *path, unsigned char output[16] )
{
FILE *f;
size_t n;
md2_context ctx;
unsigned char buf[1024];
if( ( f = fopen( path, "rb" ) ) == NULL )
return( POLARSSL_ERR_MD2_FILE_IO_ERROR );
md2_starts( &ctx );
while( ( n = fread( buf, 1, sizeof( buf ), f ) ) > 0 )
md2_update( &ctx, buf, n );
md2_finish( &ctx, output );
memset( &ctx, 0, sizeof( md2_context ) );
if( ferror( f ) != 0 )
{
fclose( f );
return( POLARSSL_ERR_MD2_FILE_IO_ERROR );
}
fclose( f );
return( 0 );
}
#endif /* POLARSSL_FS_IO */
/*
* MD2 HMAC context setup
*/
void md2_hmac_starts( md2_context *ctx, const unsigned char *key, size_t keylen )
{
size_t i;
unsigned char sum[16];
if( keylen > 16 )
{
md2( key, keylen, sum );
keylen = 16;
key = sum;
}
memset( ctx->ipad, 0x36, 16 );
memset( ctx->opad, 0x5C, 16 );
for( i = 0; i < keylen; i++ )
{
ctx->ipad[i] = (unsigned char)( ctx->ipad[i] ^ key[i] );
ctx->opad[i] = (unsigned char)( ctx->opad[i] ^ key[i] );
}
md2_starts( ctx );
md2_update( ctx, ctx->ipad, 16 );
memset( sum, 0, sizeof( sum ) );
}
/*
* MD2 HMAC process buffer
*/
void md2_hmac_update( md2_context *ctx, const unsigned char *input, size_t ilen )
{
md2_update( ctx, input, ilen );
}
/*
* MD2 HMAC final digest
*/
void md2_hmac_finish( md2_context *ctx, unsigned char output[16] )
{
unsigned char tmpbuf[16];
md2_finish( ctx, tmpbuf );
md2_starts( ctx );
md2_update( ctx, ctx->opad, 16 );
md2_update( ctx, tmpbuf, 16 );
md2_finish( ctx, output );
memset( tmpbuf, 0, sizeof( tmpbuf ) );
}
/*
* MD2 HMAC context reset
*/
void md2_hmac_reset( md2_context *ctx )
{
md2_starts( ctx );
md2_update( ctx, ctx->ipad, 16 );
}
/*
* output = HMAC-MD2( hmac key, input buffer )
*/
void md2_hmac( const unsigned char *key, size_t keylen,
const unsigned char *input, size_t ilen,
unsigned char output[16] )
{
md2_context ctx;
md2_hmac_starts( &ctx, key, keylen );
md2_hmac_update( &ctx, input, ilen );
md2_hmac_finish( &ctx, output );
memset( &ctx, 0, sizeof( md2_context ) );
}
#if defined(POLARSSL_SELF_TEST)
/*
* RFC 1319 test vectors
*/
static const char md2_test_str[7][81] =
{
{ "" },
{ "a" },
{ "abc" },
{ "message digest" },
{ "abcdefghijklmnopqrstuvwxyz" },
{ "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789" },
{ "12345678901234567890123456789012345678901234567890123456789012" \
"345678901234567890" }
};
static const unsigned char md2_test_sum[7][16] =
{
{ 0x83, 0x50, 0xE5, 0xA3, 0xE2, 0x4C, 0x15, 0x3D,
0xF2, 0x27, 0x5C, 0x9F, 0x80, 0x69, 0x27, 0x73 },
{ 0x32, 0xEC, 0x01, 0xEC, 0x4A, 0x6D, 0xAC, 0x72,
0xC0, 0xAB, 0x96, 0xFB, 0x34, 0xC0, 0xB5, 0xD1 },
{ 0xDA, 0x85, 0x3B, 0x0D, 0x3F, 0x88, 0xD9, 0x9B,
0x30, 0x28, 0x3A, 0x69, 0xE6, 0xDE, 0xD6, 0xBB },
{ 0xAB, 0x4F, 0x49, 0x6B, 0xFB, 0x2A, 0x53, 0x0B,
0x21, 0x9F, 0xF3, 0x30, 0x31, 0xFE, 0x06, 0xB0 },
{ 0x4E, 0x8D, 0xDF, 0xF3, 0x65, 0x02, 0x92, 0xAB,
0x5A, 0x41, 0x08, 0xC3, 0xAA, 0x47, 0x94, 0x0B },
{ 0xDA, 0x33, 0xDE, 0xF2, 0xA4, 0x2D, 0xF1, 0x39,
0x75, 0x35, 0x28, 0x46, 0xC3, 0x03, 0x38, 0xCD },
{ 0xD5, 0x97, 0x6F, 0x79, 0xD8, 0x3D, 0x3A, 0x0D,
0xC9, 0x80, 0x6C, 0x3C, 0x66, 0xF3, 0xEF, 0xD8 }
};
/*
* Checkup routine
*/
int md2_self_test( int verbose )
{
int i;
unsigned char md2sum[16];
for( i = 0; i < 7; i++ )
{
if( verbose != 0 )
printf( " MD2 test #%d: ", i + 1 );
md2( (unsigned char *) md2_test_str[i],
strlen( md2_test_str[i] ), md2sum );
if( memcmp( md2sum, md2_test_sum[i], 16 ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( verbose != 0 )
printf( "passed\n" );
}
if( verbose != 0 )
printf( "\n" );
return( 0 );
}
#endif
#endif
-464
View File
@@ -1,464 +0,0 @@
/*
* RFC 1186/1320 compliant MD4 implementation
*
* Copyright (C) 2006-2013, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*
* The MD4 algorithm was designed by Ron Rivest in 1990.
*
* http://www.ietf.org/rfc/rfc1186.txt
* http://www.ietf.org/rfc/rfc1320.txt
*/
#include "polarssl/config.h"
#if defined(POLARSSL_MD4_C)
#include "polarssl/md4.h"
#if defined(POLARSSL_FS_IO) || defined(POLARSSL_SELF_TEST)
#include <stdio.h>
#endif
#if !defined(POLARSSL_MD4_ALT)
/*
* 32-bit integer manipulation macros (little endian)
*/
#ifndef GET_UINT32_LE
#define GET_UINT32_LE(n,b,i) \
{ \
(n) = ( (uint32_t) (b)[(i) ] ) \
| ( (uint32_t) (b)[(i) + 1] << 8 ) \
| ( (uint32_t) (b)[(i) + 2] << 16 ) \
| ( (uint32_t) (b)[(i) + 3] << 24 ); \
}
#endif
#ifndef PUT_UINT32_LE
#define PUT_UINT32_LE(n,b,i) \
{ \
(b)[(i) ] = (unsigned char) ( (n) ); \
(b)[(i) + 1] = (unsigned char) ( (n) >> 8 ); \
(b)[(i) + 2] = (unsigned char) ( (n) >> 16 ); \
(b)[(i) + 3] = (unsigned char) ( (n) >> 24 ); \
}
#endif
/*
* MD4 context setup
*/
void md4_starts( md4_context *ctx )
{
ctx->total[0] = 0;
ctx->total[1] = 0;
ctx->state[0] = 0x67452301;
ctx->state[1] = 0xEFCDAB89;
ctx->state[2] = 0x98BADCFE;
ctx->state[3] = 0x10325476;
}
static void md4_process( md4_context *ctx, const unsigned char data[64] )
{
uint32_t X[16], A, B, C, D;
GET_UINT32_LE( X[ 0], data, 0 );
GET_UINT32_LE( X[ 1], data, 4 );
GET_UINT32_LE( X[ 2], data, 8 );
GET_UINT32_LE( X[ 3], data, 12 );
GET_UINT32_LE( X[ 4], data, 16 );
GET_UINT32_LE( X[ 5], data, 20 );
GET_UINT32_LE( X[ 6], data, 24 );
GET_UINT32_LE( X[ 7], data, 28 );
GET_UINT32_LE( X[ 8], data, 32 );
GET_UINT32_LE( X[ 9], data, 36 );
GET_UINT32_LE( X[10], data, 40 );
GET_UINT32_LE( X[11], data, 44 );
GET_UINT32_LE( X[12], data, 48 );
GET_UINT32_LE( X[13], data, 52 );
GET_UINT32_LE( X[14], data, 56 );
GET_UINT32_LE( X[15], data, 60 );
#define S(x,n) ((x << n) | ((x & 0xFFFFFFFF) >> (32 - n)))
A = ctx->state[0];
B = ctx->state[1];
C = ctx->state[2];
D = ctx->state[3];
#define F(x, y, z) ((x & y) | ((~x) & z))
#define P(a,b,c,d,x,s) { a += F(b,c,d) + x; a = S(a,s); }
P( A, B, C, D, X[ 0], 3 );
P( D, A, B, C, X[ 1], 7 );
P( C, D, A, B, X[ 2], 11 );
P( B, C, D, A, X[ 3], 19 );
P( A, B, C, D, X[ 4], 3 );
P( D, A, B, C, X[ 5], 7 );
P( C, D, A, B, X[ 6], 11 );
P( B, C, D, A, X[ 7], 19 );
P( A, B, C, D, X[ 8], 3 );
P( D, A, B, C, X[ 9], 7 );
P( C, D, A, B, X[10], 11 );
P( B, C, D, A, X[11], 19 );
P( A, B, C, D, X[12], 3 );
P( D, A, B, C, X[13], 7 );
P( C, D, A, B, X[14], 11 );
P( B, C, D, A, X[15], 19 );
#undef P
#undef F
#define F(x,y,z) ((x & y) | (x & z) | (y & z))
#define P(a,b,c,d,x,s) { a += F(b,c,d) + x + 0x5A827999; a = S(a,s); }
P( A, B, C, D, X[ 0], 3 );
P( D, A, B, C, X[ 4], 5 );
P( C, D, A, B, X[ 8], 9 );
P( B, C, D, A, X[12], 13 );
P( A, B, C, D, X[ 1], 3 );
P( D, A, B, C, X[ 5], 5 );
P( C, D, A, B, X[ 9], 9 );
P( B, C, D, A, X[13], 13 );
P( A, B, C, D, X[ 2], 3 );
P( D, A, B, C, X[ 6], 5 );
P( C, D, A, B, X[10], 9 );
P( B, C, D, A, X[14], 13 );
P( A, B, C, D, X[ 3], 3 );
P( D, A, B, C, X[ 7], 5 );
P( C, D, A, B, X[11], 9 );
P( B, C, D, A, X[15], 13 );
#undef P
#undef F
#define F(x,y,z) (x ^ y ^ z)
#define P(a,b,c,d,x,s) { a += F(b,c,d) + x + 0x6ED9EBA1; a = S(a,s); }
P( A, B, C, D, X[ 0], 3 );
P( D, A, B, C, X[ 8], 9 );
P( C, D, A, B, X[ 4], 11 );
P( B, C, D, A, X[12], 15 );
P( A, B, C, D, X[ 2], 3 );
P( D, A, B, C, X[10], 9 );
P( C, D, A, B, X[ 6], 11 );
P( B, C, D, A, X[14], 15 );
P( A, B, C, D, X[ 1], 3 );
P( D, A, B, C, X[ 9], 9 );
P( C, D, A, B, X[ 5], 11 );
P( B, C, D, A, X[13], 15 );
P( A, B, C, D, X[ 3], 3 );
P( D, A, B, C, X[11], 9 );
P( C, D, A, B, X[ 7], 11 );
P( B, C, D, A, X[15], 15 );
#undef F
#undef P
ctx->state[0] += A;
ctx->state[1] += B;
ctx->state[2] += C;
ctx->state[3] += D;
}
/*
* MD4 process buffer
*/
void md4_update( md4_context *ctx, const unsigned char *input, size_t ilen )
{
size_t fill;
uint32_t left;
if( ilen <= 0 )
return;
left = ctx->total[0] & 0x3F;
fill = 64 - left;
ctx->total[0] += (uint32_t) ilen;
ctx->total[0] &= 0xFFFFFFFF;
if( ctx->total[0] < (uint32_t) ilen )
ctx->total[1]++;
if( left && ilen >= fill )
{
memcpy( (void *) (ctx->buffer + left),
(void *) input, fill );
md4_process( ctx, ctx->buffer );
input += fill;
ilen -= fill;
left = 0;
}
while( ilen >= 64 )
{
md4_process( ctx, input );
input += 64;
ilen -= 64;
}
if( ilen > 0 )
{
memcpy( (void *) (ctx->buffer + left),
(void *) input, ilen );
}
}
static const unsigned char md4_padding[64] =
{
0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
};
/*
* MD4 final digest
*/
void md4_finish( md4_context *ctx, unsigned char output[16] )
{
uint32_t last, padn;
uint32_t high, low;
unsigned char msglen[8];
high = ( ctx->total[0] >> 29 )
| ( ctx->total[1] << 3 );
low = ( ctx->total[0] << 3 );
PUT_UINT32_LE( low, msglen, 0 );
PUT_UINT32_LE( high, msglen, 4 );
last = ctx->total[0] & 0x3F;
padn = ( last < 56 ) ? ( 56 - last ) : ( 120 - last );
md4_update( ctx, (unsigned char *) md4_padding, padn );
md4_update( ctx, msglen, 8 );
PUT_UINT32_LE( ctx->state[0], output, 0 );
PUT_UINT32_LE( ctx->state[1], output, 4 );
PUT_UINT32_LE( ctx->state[2], output, 8 );
PUT_UINT32_LE( ctx->state[3], output, 12 );
}
#endif /* !POLARSSL_MD4_ALT */
/*
* output = MD4( input buffer )
*/
void md4( const unsigned char *input, size_t ilen, unsigned char output[16] )
{
md4_context ctx;
md4_starts( &ctx );
md4_update( &ctx, input, ilen );
md4_finish( &ctx, output );
memset( &ctx, 0, sizeof( md4_context ) );
}
#if defined(POLARSSL_FS_IO)
/*
* output = MD4( file contents )
*/
int md4_file( const char *path, unsigned char output[16] )
{
FILE *f;
size_t n;
md4_context ctx;
unsigned char buf[1024];
if( ( f = fopen( path, "rb" ) ) == NULL )
return( POLARSSL_ERR_MD4_FILE_IO_ERROR );
md4_starts( &ctx );
while( ( n = fread( buf, 1, sizeof( buf ), f ) ) > 0 )
md4_update( &ctx, buf, n );
md4_finish( &ctx, output );
memset( &ctx, 0, sizeof( md4_context ) );
if( ferror( f ) != 0 )
{
fclose( f );
return( POLARSSL_ERR_MD4_FILE_IO_ERROR );
}
fclose( f );
return( 0 );
}
#endif /* POLARSSL_FS_IO */
/*
* MD4 HMAC context setup
*/
void md4_hmac_starts( md4_context *ctx, const unsigned char *key, size_t keylen )
{
size_t i;
unsigned char sum[16];
if( keylen > 64 )
{
md4( key, keylen, sum );
keylen = 16;
key = sum;
}
memset( ctx->ipad, 0x36, 64 );
memset( ctx->opad, 0x5C, 64 );
for( i = 0; i < keylen; i++ )
{
ctx->ipad[i] = (unsigned char)( ctx->ipad[i] ^ key[i] );
ctx->opad[i] = (unsigned char)( ctx->opad[i] ^ key[i] );
}
md4_starts( ctx );
md4_update( ctx, ctx->ipad, 64 );
memset( sum, 0, sizeof( sum ) );
}
/*
* MD4 HMAC process buffer
*/
void md4_hmac_update( md4_context *ctx, const unsigned char *input, size_t ilen )
{
md4_update( ctx, input, ilen );
}
/*
* MD4 HMAC final digest
*/
void md4_hmac_finish( md4_context *ctx, unsigned char output[16] )
{
unsigned char tmpbuf[16];
md4_finish( ctx, tmpbuf );
md4_starts( ctx );
md4_update( ctx, ctx->opad, 64 );
md4_update( ctx, tmpbuf, 16 );
md4_finish( ctx, output );
memset( tmpbuf, 0, sizeof( tmpbuf ) );
}
/*
* MD4 HMAC context reset
*/
void md4_hmac_reset( md4_context *ctx )
{
md4_starts( ctx );
md4_update( ctx, ctx->ipad, 64 );
}
/*
* output = HMAC-MD4( hmac key, input buffer )
*/
void md4_hmac( const unsigned char *key, size_t keylen,
const unsigned char *input, size_t ilen,
unsigned char output[16] )
{
md4_context ctx;
md4_hmac_starts( &ctx, key, keylen );
md4_hmac_update( &ctx, input, ilen );
md4_hmac_finish( &ctx, output );
memset( &ctx, 0, sizeof( md4_context ) );
}
#if defined(POLARSSL_SELF_TEST)
/*
* RFC 1320 test vectors
*/
static const char md4_test_str[7][81] =
{
{ "" },
{ "a" },
{ "abc" },
{ "message digest" },
{ "abcdefghijklmnopqrstuvwxyz" },
{ "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789" },
{ "12345678901234567890123456789012345678901234567890123456789012" \
"345678901234567890" }
};
static const unsigned char md4_test_sum[7][16] =
{
{ 0x31, 0xD6, 0xCF, 0xE0, 0xD1, 0x6A, 0xE9, 0x31,
0xB7, 0x3C, 0x59, 0xD7, 0xE0, 0xC0, 0x89, 0xC0 },
{ 0xBD, 0xE5, 0x2C, 0xB3, 0x1D, 0xE3, 0x3E, 0x46,
0x24, 0x5E, 0x05, 0xFB, 0xDB, 0xD6, 0xFB, 0x24 },
{ 0xA4, 0x48, 0x01, 0x7A, 0xAF, 0x21, 0xD8, 0x52,
0x5F, 0xC1, 0x0A, 0xE8, 0x7A, 0xA6, 0x72, 0x9D },
{ 0xD9, 0x13, 0x0A, 0x81, 0x64, 0x54, 0x9F, 0xE8,
0x18, 0x87, 0x48, 0x06, 0xE1, 0xC7, 0x01, 0x4B },
{ 0xD7, 0x9E, 0x1C, 0x30, 0x8A, 0xA5, 0xBB, 0xCD,
0xEE, 0xA8, 0xED, 0x63, 0xDF, 0x41, 0x2D, 0xA9 },
{ 0x04, 0x3F, 0x85, 0x82, 0xF2, 0x41, 0xDB, 0x35,
0x1C, 0xE6, 0x27, 0xE1, 0x53, 0xE7, 0xF0, 0xE4 },
{ 0xE3, 0x3B, 0x4D, 0xDC, 0x9C, 0x38, 0xF2, 0x19,
0x9C, 0x3E, 0x7B, 0x16, 0x4F, 0xCC, 0x05, 0x36 }
};
/*
* Checkup routine
*/
int md4_self_test( int verbose )
{
int i;
unsigned char md4sum[16];
for( i = 0; i < 7; i++ )
{
if( verbose != 0 )
printf( " MD4 test #%d: ", i + 1 );
md4( (unsigned char *) md4_test_str[i],
strlen( md4_test_str[i] ), md4sum );
if( memcmp( md4sum, md4_test_sum[i], 16 ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( verbose != 0 )
printf( "passed\n" );
}
if( verbose != 0 )
printf( "\n" );
return( 0 );
}
#endif
#endif
-374
View File
@@ -1,374 +0,0 @@
/*
* TCP networking functions
*
* Copyright (C) 2006-2010, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_NET_C)
#include "polarssl/net.h"
#if defined(_WIN32) || defined(_WIN32_WCE)
#include <winsock2.h>
#include <windows.h>
#if defined(_WIN32_WCE)
#pragma comment( lib, "ws2.lib" )
#else
#pragma comment( lib, "ws2_32.lib" )
#endif
#define read(fd,buf,len) recv(fd,(char*)buf,(int) len,0)
#define write(fd,buf,len) send(fd,(char*)buf,(int) len,0)
#define close(fd) closesocket(fd)
static int wsa_init_done = 0;
#else
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <sys/time.h>
#include <unistd.h>
#include <signal.h>
#include <fcntl.h>
#include <netdb.h>
#include <errno.h>
#if defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__NetBSD__) || \
defined(__DragonflyBSD__)
#include <sys/endian.h>
#elif defined(__APPLE__)
#include <machine/endian.h>
#elif defined(sun)
#include <sys/isa_defs.h>
#else
#include <endian.h>
#endif
#endif
#include <stdlib.h>
#include <stdio.h>
#include <time.h>
#ifdef _MSC_VER
#include <basetsd.h>
typedef UINT32 uint32_t;
#else
#include <inttypes.h>
#endif
/*
* htons() is not always available.
* By default go for LITTLE_ENDIAN variant. Otherwise hope for _BYTE_ORDER and __BIG_ENDIAN
* to help determine endianess.
*/
#if defined(__BYTE_ORDER) && defined(__BIG_ENDIAN) && __BYTE_ORDER == __BIG_ENDIAN
#define POLARSSL_HTONS(n) (n)
#define POLARSSL_HTONL(n) (n)
#else
#define POLARSSL_HTONS(n) ((((unsigned short)(n) & 0xFF ) << 8 ) | \
(((unsigned short)(n) & 0xFF00 ) >> 8 ))
#define POLARSSL_HTONL(n) ((((unsigned long )(n) & 0xFF ) << 24) | \
(((unsigned long )(n) & 0xFF00 ) << 8 ) | \
(((unsigned long )(n) & 0xFF0000 ) >> 8 ) | \
(((unsigned long )(n) & 0xFF000000) >> 24))
#endif
unsigned short net_htons(unsigned short n);
unsigned long net_htonl(unsigned long n);
#define net_htons(n) POLARSSL_HTONS(n)
#define net_htonl(n) POLARSSL_HTONL(n)
/*
* Initiate a TCP connection with host:port
*/
int net_connect( int *fd, const char *host, int port )
{
struct sockaddr_in server_addr;
struct hostent *server_host;
#if defined(_WIN32) || defined(_WIN32_WCE)
WSADATA wsaData;
if( wsa_init_done == 0 )
{
if( WSAStartup( MAKEWORD(2,0), &wsaData ) == SOCKET_ERROR )
return( POLARSSL_ERR_NET_SOCKET_FAILED );
wsa_init_done = 1;
}
#else
signal( SIGPIPE, SIG_IGN );
#endif
if( ( server_host = gethostbyname( host ) ) == NULL )
return( POLARSSL_ERR_NET_UNKNOWN_HOST );
if( ( *fd = socket( AF_INET, SOCK_STREAM, IPPROTO_IP ) ) < 0 )
return( POLARSSL_ERR_NET_SOCKET_FAILED );
memcpy( (void *) &server_addr.sin_addr,
(void *) server_host->h_addr,
server_host->h_length );
server_addr.sin_family = AF_INET;
server_addr.sin_port = net_htons( port );
if( connect( *fd, (struct sockaddr *) &server_addr,
sizeof( server_addr ) ) < 0 )
{
close( *fd );
return( POLARSSL_ERR_NET_CONNECT_FAILED );
}
return( 0 );
}
/*
* Create a listening socket on bind_ip:port
*/
int net_bind( int *fd, const char *bind_ip, int port )
{
int n, c[4];
struct sockaddr_in server_addr;
#if defined(_WIN32) || defined(_WIN32_WCE)
WSADATA wsaData;
if( wsa_init_done == 0 )
{
if( WSAStartup( MAKEWORD(2,0), &wsaData ) == SOCKET_ERROR )
return( POLARSSL_ERR_NET_SOCKET_FAILED );
wsa_init_done = 1;
}
#else
signal( SIGPIPE, SIG_IGN );
#endif
if( ( *fd = socket( AF_INET, SOCK_STREAM, IPPROTO_IP ) ) < 0 )
return( POLARSSL_ERR_NET_SOCKET_FAILED );
n = 1;
setsockopt( *fd, SOL_SOCKET, SO_REUSEADDR,
(const char *) &n, sizeof( n ) );
server_addr.sin_addr.s_addr = net_htonl( INADDR_ANY );
server_addr.sin_family = AF_INET;
server_addr.sin_port = net_htons( port );
if( bind_ip != NULL )
{
memset( c, 0, sizeof( c ) );
sscanf( bind_ip, "%d.%d.%d.%d", &c[0], &c[1], &c[2], &c[3] );
for( n = 0; n < 4; n++ )
if( c[n] < 0 || c[n] > 255 )
break;
if( n == 4 )
server_addr.sin_addr.s_addr = net_htonl(
( (uint32_t) c[0] << 24 ) |
( (uint32_t) c[1] << 16 ) |
( (uint32_t) c[2] << 8 ) |
( (uint32_t) c[3] ) );
}
if( bind( *fd, (struct sockaddr *) &server_addr,
sizeof( server_addr ) ) < 0 )
{
close( *fd );
return( POLARSSL_ERR_NET_BIND_FAILED );
}
if( listen( *fd, POLARSSL_NET_LISTEN_BACKLOG ) != 0 )
{
close( *fd );
return( POLARSSL_ERR_NET_LISTEN_FAILED );
}
return( 0 );
}
/*
* Check if the current operation is blocking
*/
static int net_is_blocking( void )
{
#if defined(_WIN32) || defined(_WIN32_WCE)
return( WSAGetLastError() == WSAEWOULDBLOCK );
#else
switch( errno )
{
#if defined EAGAIN
case EAGAIN:
#endif
#if defined EWOULDBLOCK && EWOULDBLOCK != EAGAIN
case EWOULDBLOCK:
#endif
return( 1 );
}
return( 0 );
#endif
}
/*
* Accept a connection from a remote client
*/
int net_accept( int bind_fd, int *client_fd, void *client_ip )
{
struct sockaddr_in client_addr;
#if defined(__socklen_t_defined) || defined(_SOCKLEN_T) || \
defined(_SOCKLEN_T_DECLARED)
socklen_t n = (socklen_t) sizeof( client_addr );
#else
int n = (int) sizeof( client_addr );
#endif
*client_fd = accept( bind_fd, (struct sockaddr *)
&client_addr, &n );
if( *client_fd < 0 )
{
if( net_is_blocking() != 0 )
return( POLARSSL_ERR_NET_WANT_READ );
return( POLARSSL_ERR_NET_ACCEPT_FAILED );
}
if( client_ip != NULL )
memcpy( client_ip, &client_addr.sin_addr.s_addr,
sizeof( client_addr.sin_addr.s_addr ) );
return( 0 );
}
/*
* Set the socket blocking or non-blocking
*/
int net_set_block( int fd )
{
#if defined(_WIN32) || defined(_WIN32_WCE)
u_long n = 0;
return( ioctlsocket( fd, FIONBIO, &n ) );
#else
return( fcntl( fd, F_SETFL, fcntl( fd, F_GETFL ) & ~O_NONBLOCK ) );
#endif
}
int net_set_nonblock( int fd )
{
#if defined(_WIN32) || defined(_WIN32_WCE)
u_long n = 1;
return( ioctlsocket( fd, FIONBIO, &n ) );
#else
return( fcntl( fd, F_SETFL, fcntl( fd, F_GETFL ) | O_NONBLOCK ) );
#endif
}
/*
* Portable usleep helper
*/
void net_usleep( unsigned long usec )
{
struct timeval tv;
tv.tv_sec = 0;
tv.tv_usec = usec;
select( 0, NULL, NULL, NULL, &tv );
}
/*
* Read at most 'len' characters
*/
int net_recv( void *ctx, unsigned char *buf, size_t len )
{
int ret = read( *((int *) ctx), buf, len );
if( ret < 0 )
{
if( net_is_blocking() != 0 )
return( POLARSSL_ERR_NET_WANT_READ );
#if defined(_WIN32) || defined(_WIN32_WCE)
if( WSAGetLastError() == WSAECONNRESET )
return( POLARSSL_ERR_NET_CONN_RESET );
#else
if( errno == EPIPE || errno == ECONNRESET )
return( POLARSSL_ERR_NET_CONN_RESET );
if( errno == EINTR )
return( POLARSSL_ERR_NET_WANT_READ );
#endif
return( POLARSSL_ERR_NET_RECV_FAILED );
}
return( ret );
}
/*
* Write at most 'len' characters
*/
int net_send( void *ctx, const unsigned char *buf, size_t len )
{
int ret = write( *((int *) ctx), buf, len );
if( ret < 0 )
{
if( net_is_blocking() != 0 )
return( POLARSSL_ERR_NET_WANT_WRITE );
#if defined(_WIN32) || defined(_WIN32_WCE)
if( WSAGetLastError() == WSAECONNRESET )
return( POLARSSL_ERR_NET_CONN_RESET );
#else
if( errno == EPIPE || errno == ECONNRESET )
return( POLARSSL_ERR_NET_CONN_RESET );
if( errno == EINTR )
return( POLARSSL_ERR_NET_WANT_WRITE );
#endif
return( POLARSSL_ERR_NET_SEND_FAILED );
}
return( ret );
}
/*
* Gracefully close the connection
*/
void net_close( int fd )
{
shutdown( fd, 2 );
close( fd );
}
#endif
-162
View File
@@ -1,162 +0,0 @@
/*
* VIA PadLock support functions
*
* Copyright (C) 2006-2010, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*
* This implementation is based on the VIA PadLock Programming Guide:
*
* http://www.via.com.tw/en/downloads/whitepapers/initiatives/padlock/
* programming_guide.pdf
*/
#include "polarssl/config.h"
#if defined(POLARSSL_PADLOCK_C)
#include "polarssl/padlock.h"
#if defined(POLARSSL_HAVE_X86)
/*
* PadLock detection routine
*/
int padlock_supports( int feature )
{
static int flags = -1;
int ebx, edx;
if( flags == -1 )
{
__asm__( "movl %%ebx, %0 \n" \
"movl $0xC0000000, %%eax \n" \
"cpuid \n" \
"cmpl $0xC0000001, %%eax \n" \
"movl $0, %%edx \n" \
"jb unsupported \n" \
"movl $0xC0000001, %%eax \n" \
"cpuid \n" \
"unsupported: \n" \
"movl %%edx, %1 \n" \
"movl %2, %%ebx \n"
: "=m" (ebx), "=m" (edx)
: "m" (ebx)
: "eax", "ecx", "edx" );
flags = edx;
}
return( flags & feature );
}
/*
* PadLock AES-ECB block en(de)cryption
*/
int padlock_xcryptecb( aes_context *ctx,
int mode,
const unsigned char input[16],
unsigned char output[16] )
{
int ebx;
uint32_t *rk;
uint32_t *blk;
uint32_t *ctrl;
unsigned char buf[256];
rk = ctx->rk;
blk = PADLOCK_ALIGN16( buf );
memcpy( blk, input, 16 );
ctrl = blk + 4;
*ctrl = 0x80 | ctx->nr | ( ( ctx->nr + ( mode^1 ) - 10 ) << 9 );
__asm__( "pushfl; popfl \n" \
"movl %%ebx, %0 \n" \
"movl $1, %%ecx \n" \
"movl %2, %%edx \n" \
"movl %3, %%ebx \n" \
"movl %4, %%esi \n" \
"movl %4, %%edi \n" \
".byte 0xf3,0x0f,0xa7,0xc8\n" \
"movl %1, %%ebx \n"
: "=m" (ebx)
: "m" (ebx), "m" (ctrl), "m" (rk), "m" (blk)
: "ecx", "edx", "esi", "edi" );
memcpy( output, blk, 16 );
return( 0 );
}
/*
* PadLock AES-CBC buffer en(de)cryption
*/
int padlock_xcryptcbc( aes_context *ctx,
int mode,
size_t length,
unsigned char iv[16],
const unsigned char *input,
unsigned char *output )
{
int ebx;
size_t count;
uint32_t *rk;
uint32_t *iw;
uint32_t *ctrl;
unsigned char buf[256];
if( ( (long) input & 15 ) != 0 ||
( (long) output & 15 ) != 0 )
return( POLARSSL_ERR_PADLOCK_DATA_MISALIGNED );
rk = ctx->rk;
iw = PADLOCK_ALIGN16( buf );
memcpy( iw, iv, 16 );
ctrl = iw + 4;
*ctrl = 0x80 | ctx->nr | ( ( ctx->nr + (mode^1) - 10 ) << 9 );
count = (length + 15) >> 4;
__asm__( "pushfl; popfl \n" \
"movl %%ebx, %0 \n" \
"movl %2, %%ecx \n" \
"movl %3, %%edx \n" \
"movl %4, %%ebx \n" \
"movl %5, %%esi \n" \
"movl %6, %%edi \n" \
"movl %7, %%eax \n" \
".byte 0xf3,0x0f,0xa7,0xd0\n" \
"movl %1, %%ebx \n"
: "=m" (ebx)
: "m" (ebx), "m" (count), "m" (ctrl),
"m" (rk), "m" (input), "m" (output), "m" (iw)
: "eax", "ecx", "edx", "esi", "edi" );
memcpy( iv, iw, 16 );
return( 0 );
}
#endif
#endif
-60
View File
@@ -1,60 +0,0 @@
/**
* \file pbkdf2.c
*
* \brief Password-Based Key Derivation Function 2 (from PKCS#5)
* DEPRECATED: Use pkcs5.c instead
*
* \author Mathias Olsson <mathias@kompetensum.com>
*
* Copyright (C) 2006-2012, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*
* PBKDF2 is part of PKCS#5
*
* http://tools.ietf.org/html/rfc2898 (Specification)
* http://tools.ietf.org/html/rfc6070 (Test vectors)
*/
#include "polarssl/config.h"
#if defined(POLARSSL_PBKDF2_C)
#include "polarssl/pbkdf2.h"
#include "polarssl/pkcs5.h"
int pbkdf2_hmac( md_context_t *ctx, const unsigned char *password, size_t plen,
const unsigned char *salt, size_t slen,
unsigned int iteration_count,
uint32_t key_length, unsigned char *output )
{
return pkcs5_pbkdf2_hmac( ctx, password, plen, salt, slen, iteration_count,
key_length, output );
}
#if defined(POLARSSL_SELF_TEST)
int pbkdf2_self_test( int verbose )
{
return pkcs5_self_test( verbose );
}
#endif /* POLARSSL_SELF_TEST */
#endif /* POLARSSL_PBKDF2_C */
-355
View File
@@ -1,355 +0,0 @@
/*
* Privacy Enhanced Mail (PEM) decoding
*
* Copyright (C) 2006-2013, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_PEM_C)
#include "polarssl/pem.h"
#include "polarssl/base64.h"
#include "polarssl/des.h"
#include "polarssl/aes.h"
#include "polarssl/md5.h"
#include "polarssl/cipher.h"
#include <stdlib.h>
void pem_init( pem_context *ctx )
{
memset( ctx, 0, sizeof( pem_context ) );
}
#if defined(POLARSSL_MD5_C) && (defined(POLARSSL_DES_C) || defined(POLARSSL_AES_C))
/*
* Read a 16-byte hex string and convert it to binary
*/
static int pem_get_iv( const unsigned char *s, unsigned char *iv, size_t iv_len )
{
size_t i, j, k;
memset( iv, 0, iv_len );
for( i = 0; i < iv_len * 2; i++, s++ )
{
if( *s >= '0' && *s <= '9' ) j = *s - '0'; else
if( *s >= 'A' && *s <= 'F' ) j = *s - '7'; else
if( *s >= 'a' && *s <= 'f' ) j = *s - 'W'; else
return( POLARSSL_ERR_PEM_INVALID_ENC_IV );
k = ( ( i & 1 ) != 0 ) ? j : j << 4;
iv[i >> 1] = (unsigned char)( iv[i >> 1] | k );
}
return( 0 );
}
static void pem_pbkdf1( unsigned char *key, size_t keylen,
unsigned char *iv,
const unsigned char *pwd, size_t pwdlen )
{
md5_context md5_ctx;
unsigned char md5sum[16];
size_t use_len;
/*
* key[ 0..15] = MD5(pwd || IV)
*/
md5_starts( &md5_ctx );
md5_update( &md5_ctx, pwd, pwdlen );
md5_update( &md5_ctx, iv, 8 );
md5_finish( &md5_ctx, md5sum );
if( keylen <= 16 )
{
memcpy( key, md5sum, keylen );
memset( &md5_ctx, 0, sizeof( md5_ctx ) );
memset( md5sum, 0, 16 );
return;
}
memcpy( key, md5sum, 16 );
/*
* key[16..23] = MD5(key[ 0..15] || pwd || IV])
*/
md5_starts( &md5_ctx );
md5_update( &md5_ctx, md5sum, 16 );
md5_update( &md5_ctx, pwd, pwdlen );
md5_update( &md5_ctx, iv, 8 );
md5_finish( &md5_ctx, md5sum );
use_len = 16;
if( keylen < 32 )
use_len = keylen - 16;
memcpy( key + 16, md5sum, use_len );
memset( &md5_ctx, 0, sizeof( md5_ctx ) );
memset( md5sum, 0, 16 );
}
#if defined(POLARSSL_DES_C)
/*
* Decrypt with DES-CBC, using PBKDF1 for key derivation
*/
static void pem_des_decrypt( unsigned char des_iv[8],
unsigned char *buf, size_t buflen,
const unsigned char *pwd, size_t pwdlen )
{
des_context des_ctx;
unsigned char des_key[8];
pem_pbkdf1( des_key, 8, des_iv, pwd, pwdlen );
des_setkey_dec( &des_ctx, des_key );
des_crypt_cbc( &des_ctx, DES_DECRYPT, buflen,
des_iv, buf, buf );
memset( &des_ctx, 0, sizeof( des_ctx ) );
memset( des_key, 0, 8 );
}
/*
* Decrypt with 3DES-CBC, using PBKDF1 for key derivation
*/
static void pem_des3_decrypt( unsigned char des3_iv[8],
unsigned char *buf, size_t buflen,
const unsigned char *pwd, size_t pwdlen )
{
des3_context des3_ctx;
unsigned char des3_key[24];
pem_pbkdf1( des3_key, 24, des3_iv, pwd, pwdlen );
des3_set3key_dec( &des3_ctx, des3_key );
des3_crypt_cbc( &des3_ctx, DES_DECRYPT, buflen,
des3_iv, buf, buf );
memset( &des3_ctx, 0, sizeof( des3_ctx ) );
memset( des3_key, 0, 24 );
}
#endif /* POLARSSL_DES_C */
#if defined(POLARSSL_AES_C)
/*
* Decrypt with AES-XXX-CBC, using PBKDF1 for key derivation
*/
static void pem_aes_decrypt( unsigned char aes_iv[16], unsigned int keylen,
unsigned char *buf, size_t buflen,
const unsigned char *pwd, size_t pwdlen )
{
aes_context aes_ctx;
unsigned char aes_key[32];
pem_pbkdf1( aes_key, keylen, aes_iv, pwd, pwdlen );
aes_setkey_dec( &aes_ctx, aes_key, keylen * 8 );
aes_crypt_cbc( &aes_ctx, AES_DECRYPT, buflen,
aes_iv, buf, buf );
memset( &aes_ctx, 0, sizeof( aes_ctx ) );
memset( aes_key, 0, keylen );
}
#endif /* POLARSSL_AES_C */
#endif /* POLARSSL_MD5_C && (POLARSSL_AES_C || POLARSSL_DES_C) */
int pem_read_buffer( pem_context *ctx, char *header, char *footer, const unsigned char *data, const unsigned char *pwd, size_t pwdlen, size_t *use_len )
{
int ret, enc;
size_t len;
unsigned char *buf;
const unsigned char *s1, *s2, *end;
#if defined(POLARSSL_MD5_C) && (defined(POLARSSL_DES_C) || defined(POLARSSL_AES_C))
unsigned char pem_iv[16];
cipher_type_t enc_alg = POLARSSL_CIPHER_NONE;
#else
((void) pwd);
((void) pwdlen);
#endif /* POLARSSL_MD5_C && (POLARSSL_AES_C || POLARSSL_DES_C) */
if( ctx == NULL )
return( POLARSSL_ERR_PEM_BAD_INPUT_DATA );
s1 = (unsigned char *) strstr( (const char *) data, header );
if( s1 == NULL )
return( POLARSSL_ERR_PEM_NO_HEADER_FOOTER_PRESENT );
s2 = (unsigned char *) strstr( (const char *) data, footer );
if( s2 == NULL || s2 <= s1 )
return( POLARSSL_ERR_PEM_NO_HEADER_FOOTER_PRESENT );
s1 += strlen( header );
if( *s1 == '\r' ) s1++;
if( *s1 == '\n' ) s1++;
else return( POLARSSL_ERR_PEM_NO_HEADER_FOOTER_PRESENT );
end = s2;
end += strlen( footer );
if( *end == '\r' ) end++;
if( *end == '\n' ) end++;
*use_len = end - data;
enc = 0;
if( memcmp( s1, "Proc-Type: 4,ENCRYPTED", 22 ) == 0 )
{
#if defined(POLARSSL_MD5_C) && (defined(POLARSSL_DES_C) || defined(POLARSSL_AES_C))
enc++;
s1 += 22;
if( *s1 == '\r' ) s1++;
if( *s1 == '\n' ) s1++;
else return( POLARSSL_ERR_PEM_INVALID_DATA );
#if defined(POLARSSL_DES_C)
if( memcmp( s1, "DEK-Info: DES-EDE3-CBC,", 23 ) == 0 )
{
enc_alg = POLARSSL_CIPHER_DES_EDE3_CBC;
s1 += 23;
if( pem_get_iv( s1, pem_iv, 8 ) != 0 )
return( POLARSSL_ERR_PEM_INVALID_ENC_IV );
s1 += 16;
}
else if( memcmp( s1, "DEK-Info: DES-CBC,", 18 ) == 0 )
{
enc_alg = POLARSSL_CIPHER_DES_CBC;
s1 += 18;
if( pem_get_iv( s1, pem_iv, 8) != 0 )
return( POLARSSL_ERR_PEM_INVALID_ENC_IV );
s1 += 16;
}
#endif /* POLARSSL_DES_C */
#if defined(POLARSSL_AES_C)
if( memcmp( s1, "DEK-Info: AES-", 14 ) == 0 )
{
if( memcmp( s1, "DEK-Info: AES-128-CBC,", 22 ) == 0 )
enc_alg = POLARSSL_CIPHER_AES_128_CBC;
else if( memcmp( s1, "DEK-Info: AES-192-CBC,", 22 ) == 0 )
enc_alg = POLARSSL_CIPHER_AES_192_CBC;
else if( memcmp( s1, "DEK-Info: AES-256-CBC,", 22 ) == 0 )
enc_alg = POLARSSL_CIPHER_AES_256_CBC;
else
return( POLARSSL_ERR_PEM_UNKNOWN_ENC_ALG );
s1 += 22;
if( pem_get_iv( s1, pem_iv, 16 ) != 0 )
return( POLARSSL_ERR_PEM_INVALID_ENC_IV );
s1 += 32;
}
#endif /* POLARSSL_AES_C */
if( enc_alg == POLARSSL_CIPHER_NONE )
return( POLARSSL_ERR_PEM_UNKNOWN_ENC_ALG );
if( *s1 == '\r' ) s1++;
if( *s1 == '\n' ) s1++;
else return( POLARSSL_ERR_PEM_INVALID_DATA );
#else
return( POLARSSL_ERR_PEM_FEATURE_UNAVAILABLE );
#endif /* POLARSSL_MD5_C && (POLARSSL_AES_C || POLARSSL_DES_C) */
}
len = 0;
ret = base64_decode( NULL, &len, s1, s2 - s1 );
if( ret == POLARSSL_ERR_BASE64_INVALID_CHARACTER )
return( POLARSSL_ERR_PEM_INVALID_DATA + ret );
if( ( buf = (unsigned char *) malloc( len ) ) == NULL )
return( POLARSSL_ERR_PEM_MALLOC_FAILED );
if( ( ret = base64_decode( buf, &len, s1, s2 - s1 ) ) != 0 )
{
free( buf );
return( POLARSSL_ERR_PEM_INVALID_DATA + ret );
}
if( enc != 0 )
{
#if defined(POLARSSL_MD5_C) && (defined(POLARSSL_DES_C) || defined(POLARSSL_AES_C))
if( pwd == NULL )
{
free( buf );
return( POLARSSL_ERR_PEM_PASSWORD_REQUIRED );
}
#if defined(POLARSSL_DES_C)
if( enc_alg == POLARSSL_CIPHER_DES_EDE3_CBC )
pem_des3_decrypt( pem_iv, buf, len, pwd, pwdlen );
else if( enc_alg == POLARSSL_CIPHER_DES_CBC )
pem_des_decrypt( pem_iv, buf, len, pwd, pwdlen );
#endif /* POLARSSL_DES_C */
#if defined(POLARSSL_AES_C)
if( enc_alg == POLARSSL_CIPHER_AES_128_CBC )
pem_aes_decrypt( pem_iv, 16, buf, len, pwd, pwdlen );
else if( enc_alg == POLARSSL_CIPHER_AES_192_CBC )
pem_aes_decrypt( pem_iv, 24, buf, len, pwd, pwdlen );
else if( enc_alg == POLARSSL_CIPHER_AES_256_CBC )
pem_aes_decrypt( pem_iv, 32, buf, len, pwd, pwdlen );
#endif /* POLARSSL_AES_C */
if( buf[0] != 0x30 || buf[1] != 0x82 ||
buf[4] != 0x02 || buf[5] != 0x01 )
{
free( buf );
return( POLARSSL_ERR_PEM_PASSWORD_MISMATCH );
}
#else
free( buf );
return( POLARSSL_ERR_PEM_FEATURE_UNAVAILABLE );
#endif
}
ctx->buf = buf;
ctx->buflen = len;
return( 0 );
}
void pem_free( pem_context *ctx )
{
if( ctx->buf )
free( ctx->buf );
if( ctx->info )
free( ctx->info );
memset( ctx, 0, sizeof( pem_context ) );
}
#endif
-238
View File
@@ -1,238 +0,0 @@
/**
* \file pkcs11.c
*
* \brief Wrapper for PKCS#11 library libpkcs11-helper
*
* \author Adriaan de Jong <dejong@fox-it.com>
*
* Copyright (C) 2006-2010, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/pkcs11.h"
#if defined(POLARSSL_PKCS11_C)
#include <stdlib.h>
int pkcs11_x509_cert_init( x509_cert *cert, pkcs11h_certificate_t pkcs11_cert )
{
int ret = 1;
unsigned char *cert_blob = NULL;
size_t cert_blob_size = 0;
if( cert == NULL )
{
ret = 2;
goto cleanup;
}
if( pkcs11h_certificate_getCertificateBlob( pkcs11_cert, NULL, &cert_blob_size ) != CKR_OK )
{
ret = 3;
goto cleanup;
}
cert_blob = malloc( cert_blob_size );
if( NULL == cert_blob )
{
ret = 4;
goto cleanup;
}
if( pkcs11h_certificate_getCertificateBlob( pkcs11_cert, cert_blob, &cert_blob_size ) != CKR_OK )
{
ret = 5;
goto cleanup;
}
if( 0 != x509parse_crt(cert, cert_blob, cert_blob_size ) )
{
ret = 6;
goto cleanup;
}
ret = 0;
cleanup:
if( NULL != cert_blob )
free( cert_blob );
return ret;
}
int pkcs11_priv_key_init( pkcs11_context *priv_key,
pkcs11h_certificate_t pkcs11_cert )
{
int ret = 1;
x509_cert cert;
memset( &cert, 0, sizeof( cert ) );
if( priv_key == NULL )
goto cleanup;
if( 0 != pkcs11_x509_cert_init( &cert, pkcs11_cert ) )
goto cleanup;
priv_key->len = cert.rsa.len;
priv_key->pkcs11h_cert = pkcs11_cert;
ret = 0;
cleanup:
x509_free( &cert );
return ret;
}
void pkcs11_priv_key_free( pkcs11_context *priv_key )
{
if( NULL != priv_key )
pkcs11h_certificate_freeCertificate( priv_key->pkcs11h_cert );
}
int pkcs11_decrypt( pkcs11_context *ctx,
int mode, size_t *olen,
const unsigned char *input,
unsigned char *output,
size_t output_max_len )
{
size_t input_len, output_len;
if( NULL == ctx )
return( POLARSSL_ERR_RSA_BAD_INPUT_DATA );
if( RSA_PUBLIC == mode )
return( POLARSSL_ERR_RSA_BAD_INPUT_DATA );
output_len = input_len = ctx->len;
if( input_len < 16 || input_len > output_max_len )
return( POLARSSL_ERR_RSA_BAD_INPUT_DATA );
/* Determine size of output buffer */
if( pkcs11h_certificate_decryptAny( ctx->pkcs11h_cert, CKM_RSA_PKCS, input,
input_len, NULL, &output_len ) != CKR_OK )
{
return( POLARSSL_ERR_RSA_BAD_INPUT_DATA );
}
if( output_len > output_max_len )
return( POLARSSL_ERR_RSA_OUTPUT_TOO_LARGE );
if( pkcs11h_certificate_decryptAny( ctx->pkcs11h_cert, CKM_RSA_PKCS, input,
input_len, output, &output_len ) != CKR_OK )
{
return( POLARSSL_ERR_RSA_BAD_INPUT_DATA );
}
*olen = output_len;
return( 0 );
}
int pkcs11_sign( pkcs11_context *ctx,
int mode,
int hash_id,
unsigned int hashlen,
const unsigned char *hash,
unsigned char *sig )
{
size_t olen, asn_len;
unsigned char *p = sig;
if( NULL == ctx )
return POLARSSL_ERR_RSA_BAD_INPUT_DATA;
if( RSA_PUBLIC == mode )
return POLARSSL_ERR_RSA_BAD_INPUT_DATA;
olen = ctx->len;
switch( hash_id )
{
case SIG_RSA_RAW:
asn_len = 0;
memcpy( p, hash, hashlen );
break;
case SIG_RSA_MD2:
asn_len = OID_SIZE(ASN1_HASH_MDX);
memcpy( p, ASN1_HASH_MDX, asn_len );
memcpy( p + asn_len, hash, hashlen );
p[13] = 2; break;
case SIG_RSA_MD4:
asn_len = OID_SIZE(ASN1_HASH_MDX);
memcpy( p, ASN1_HASH_MDX, asn_len );
memcpy( p + asn_len, hash, hashlen );
p[13] = 4; break;
case SIG_RSA_MD5:
asn_len = OID_SIZE(ASN1_HASH_MDX);
memcpy( p, ASN1_HASH_MDX, asn_len );
memcpy( p + asn_len, hash, hashlen );
p[13] = 5; break;
case SIG_RSA_SHA1:
asn_len = OID_SIZE(ASN1_HASH_SHA1);
memcpy( p, ASN1_HASH_SHA1, asn_len );
memcpy( p + 15, hash, hashlen );
break;
case SIG_RSA_SHA224:
asn_len = OID_SIZE(ASN1_HASH_SHA2X);
memcpy( p, ASN1_HASH_SHA2X, asn_len );
memcpy( p + asn_len, hash, hashlen );
p[1] += hashlen; p[14] = 4; p[18] += hashlen; break;
case SIG_RSA_SHA256:
asn_len = OID_SIZE(ASN1_HASH_SHA2X);
memcpy( p, ASN1_HASH_SHA2X, asn_len );
memcpy( p + asn_len, hash, hashlen );
p[1] += hashlen; p[14] = 1; p[18] += hashlen; break;
case SIG_RSA_SHA384:
asn_len = OID_SIZE(ASN1_HASH_SHA2X);
memcpy( p, ASN1_HASH_SHA2X, asn_len );
memcpy( p + asn_len, hash, hashlen );
p[1] += hashlen; p[14] = 2; p[18] += hashlen; break;
case SIG_RSA_SHA512:
asn_len = OID_SIZE(ASN1_HASH_SHA2X);
memcpy( p, ASN1_HASH_SHA2X, asn_len );
memcpy( p + asn_len, hash, hashlen );
p[1] += hashlen; p[14] = 3; p[18] += hashlen; break;
default:
return( POLARSSL_ERR_RSA_BAD_INPUT_DATA );
}
if( pkcs11h_certificate_signAny( ctx->pkcs11h_cert, CKM_RSA_PKCS, sig,
asn_len + hashlen, sig, &olen ) != CKR_OK )
{
return( POLARSSL_ERR_RSA_BAD_INPUT_DATA );
}
return( 0 );
}
#endif /* defined(POLARSSL_PKCS11_C) */
-330
View File
@@ -1,330 +0,0 @@
/*
* PKCS#12 Personal Information Exchange Syntax
*
* Copyright (C) 2006-2013, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*
* The PKCS #12 Personal Information Exchange Syntax Standard v1.1
*
* http://www.rsa.com/rsalabs/pkcs/files/h11301-wp-pkcs-12v1-1-personal-information-exchange-syntax.pdf
* ftp://ftp.rsasecurity.com/pub/pkcs/pkcs-12/pkcs-12v1-1.asn
*/
#include "polarssl/config.h"
#if defined(POLARSSL_PKCS12_C)
#include "polarssl/pkcs12.h"
#include "polarssl/asn1.h"
#include "polarssl/cipher.h"
#if defined(POLARSSL_ARC4_C)
#include "polarssl/arc4.h"
#endif
#if defined(POLARSSL_DES_C)
#include "polarssl/des.h"
#endif
static int pkcs12_parse_pbe_params( unsigned char **p,
const unsigned char *end,
asn1_buf *salt, int *iterations )
{
int ret;
size_t len = 0;
/*
* pkcs-12PbeParams ::= SEQUENCE {
* salt OCTET STRING,
* iterations INTEGER
* }
*
*/
if( ( ret = asn1_get_tag( p, end, &len,
ASN1_CONSTRUCTED | ASN1_SEQUENCE ) ) != 0 )
{
return( POLARSSL_ERR_PKCS12_PBE_INVALID_FORMAT + ret );
}
end = *p + len;
if( ( ret = asn1_get_tag( p, end, &salt->len, ASN1_OCTET_STRING ) ) != 0 )
return( POLARSSL_ERR_PKCS12_PBE_INVALID_FORMAT + ret );
salt->p = *p;
*p += salt->len;
if( ( ret = asn1_get_int( p, end, iterations ) ) != 0 )
return( POLARSSL_ERR_PKCS12_PBE_INVALID_FORMAT + ret );
if( *p != end )
return( POLARSSL_ERR_PKCS12_PBE_INVALID_FORMAT +
POLARSSL_ERR_ASN1_LENGTH_MISMATCH );
return( 0 );
}
static int pkcs12_pbe_derive_key_iv( asn1_buf *pbe_params, md_type_t md_type,
const unsigned char *pwd, size_t pwdlen,
unsigned char *key, size_t keylen,
unsigned char *iv, size_t ivlen )
{
int ret, iterations;
asn1_buf salt;
size_t i;
unsigned char *p, *end;
unsigned char unipwd[258];
memset(&salt, 0, sizeof(asn1_buf));
memset(&unipwd, 0, sizeof(unipwd));
p = pbe_params->p;
end = p + pbe_params->len;
if( ( ret = pkcs12_parse_pbe_params( &p, end, &salt, &iterations ) ) != 0 )
return( ret );
for(i = 0; i < pwdlen; i++)
unipwd[i * 2 + 1] = pwd[i];
if( ( ret = pkcs12_derivation( key, keylen, unipwd, pwdlen * 2 + 2,
salt.p, salt.len, md_type,
PKCS12_DERIVE_KEY, iterations ) ) != 0 )
{
return( ret );
}
if( iv == NULL || ivlen == 0 )
return( 0 );
if( ( ret = pkcs12_derivation( iv, ivlen, unipwd, pwdlen * 2 + 2,
salt.p, salt.len, md_type,
PKCS12_DERIVE_IV, iterations ) ) != 0 )
{
return( ret );
}
return( 0 );
}
int pkcs12_pbe_sha1_rc4_128( asn1_buf *pbe_params, int mode,
const unsigned char *pwd, size_t pwdlen,
const unsigned char *data, size_t len,
unsigned char *output )
{
#if !defined(POLARSSL_ARC4_C)
((void) pbe_params);
((void) mode);
((void) pwd);
((void) pwdlen);
((void) data);
((void) len);
((void) output);
return( POLARSSL_ERR_PKCS12_FEATURE_UNAVAILABLE );
#else
int ret;
unsigned char key[16];
arc4_context ctx;
((void) mode);
if( ( ret = pkcs12_pbe_derive_key_iv( pbe_params, POLARSSL_MD_SHA1,
pwd, pwdlen,
key, 16, NULL, 0 ) ) != 0 )
{
return( ret );
}
arc4_setup( &ctx, key, 16 );
if( ( ret = arc4_crypt( &ctx, len, data, output ) ) != 0 )
return( ret );
return( 0 );
#endif /* POLARSSL_ARC4_C */
}
int pkcs12_pbe( asn1_buf *pbe_params, int mode,
cipher_type_t cipher_type, md_type_t md_type,
const unsigned char *pwd, size_t pwdlen,
const unsigned char *data, size_t len,
unsigned char *output )
{
int ret, keylen = 0;
unsigned char key[32];
unsigned char iv[16];
const cipher_info_t *cipher_info;
cipher_context_t cipher_ctx;
size_t olen = 0;
cipher_info = cipher_info_from_type( cipher_type );
if( cipher_info == NULL )
return( POLARSSL_ERR_PKCS12_FEATURE_UNAVAILABLE );
keylen = cipher_info->key_length / 8;
if( ( ret = pkcs12_pbe_derive_key_iv( pbe_params, md_type, pwd, pwdlen,
key, keylen,
iv, cipher_info->iv_size ) ) != 0 )
{
return( ret );
}
if( ( ret = cipher_init_ctx( &cipher_ctx, cipher_info ) ) != 0 )
return( ret );
if( ( ret = cipher_setkey( &cipher_ctx, key, keylen, mode ) ) != 0 )
return( ret );
if( ( ret = cipher_reset( &cipher_ctx, iv ) ) != 0 )
return( ret );
if( ( ret = cipher_update( &cipher_ctx, data, len,
output, &olen ) ) != 0 )
{
return( ret );
}
if( ( ret = cipher_finish( &cipher_ctx, output + olen, &olen ) ) != 0 )
return( POLARSSL_ERR_PKCS12_PASSWORD_MISMATCH );
return( 0 );
}
static void pkcs12_fill_buffer( unsigned char *data, size_t data_len,
const unsigned char *filler, size_t fill_len )
{
unsigned char *p = data;
size_t use_len;
while( data_len > 0 )
{
use_len = ( data_len > fill_len ) ? fill_len : data_len;
memcpy( p, filler, use_len );
p += use_len;
data_len -= use_len;
}
}
int pkcs12_derivation( unsigned char *data, size_t datalen,
const unsigned char *pwd, size_t pwdlen,
const unsigned char *salt, size_t saltlen,
md_type_t md_type, int id, int iterations )
{
int ret, i;
unsigned int j;
unsigned char diversifier[128];
unsigned char salt_block[128], pwd_block[128], hash_block[128];
unsigned char hash_output[POLARSSL_MD_MAX_SIZE];
unsigned char *p;
unsigned char c;
size_t hlen, use_len, v;
const md_info_t *md_info;
md_context_t md_ctx;
// This version only allows max of 64 bytes of password or salt
if( datalen > 128 || pwdlen > 64 || saltlen > 64 )
return( POLARSSL_ERR_PKCS12_BAD_INPUT_DATA );
md_info = md_info_from_type( md_type );
if( md_info == NULL )
return( POLARSSL_ERR_PKCS12_FEATURE_UNAVAILABLE );
if ( ( ret = md_init_ctx( &md_ctx, md_info ) ) != 0 )
return( ret );
hlen = md_get_size( md_info );
if( hlen <= 32 )
v = 64;
else
v = 128;
memset( diversifier, (unsigned char) id, v );
pkcs12_fill_buffer( salt_block, v, salt, saltlen );
pkcs12_fill_buffer( pwd_block, v, pwd, pwdlen );
p = data;
while( datalen > 0 )
{
// Calculate hash( diversifier || salt_block || pwd_block )
if( ( ret = md_starts( &md_ctx ) ) != 0 )
return( ret );
if( ( ret = md_update( &md_ctx, diversifier, v ) ) != 0 )
return( ret );
if( ( ret = md_update( &md_ctx, salt_block, v ) ) != 0 )
return( ret );
if( ( ret = md_update( &md_ctx, pwd_block, v ) ) != 0 )
return( ret );
if( ( ret = md_finish( &md_ctx, hash_output ) ) != 0 )
return( ret );
// Perform remaining ( iterations - 1 ) recursive hash calculations
for( i = 1; i < iterations; i++ )
{
if( ( ret = md( md_info, hash_output, hlen, hash_output ) ) != 0 )
return( ret );
}
use_len = ( datalen > hlen ) ? hlen : datalen;
memcpy( p, hash_output, use_len );
datalen -= use_len;
p += use_len;
if( datalen == 0 )
break;
// Concatenating copies of hash_output into hash_block (B)
pkcs12_fill_buffer( hash_block, v, hash_output, hlen );
// B += 1
for( i = v; i > 0; i-- )
if( ++hash_block[i - 1] != 0 )
break;
// salt_block += B
c = 0;
for( i = v; i > 0; i-- )
{
j = salt_block[i - 1] + hash_block[i - 1] + c;
c = (unsigned char) (j >> 8);
salt_block[i - 1] = j & 0xFF;
}
// pwd_block += B
c = 0;
for( i = v; i > 0; i-- )
{
j = pwd_block[i - 1] + hash_block[i - 1] + c;
c = (unsigned char) (j >> 8);
pwd_block[i - 1] = j & 0xFF;
}
}
return( 0 );
}
#endif /* POLARSSL_PKCS12_C */
-415
View File
@@ -1,415 +0,0 @@
/**
* \file pkcs5.c
*
* \brief PKCS#5 functions
*
* \author Mathias Olsson <mathias@kompetensum.com>
*
* Copyright (C) 2006-2013, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*
* PKCS#5 includes PBKDF2 and more
*
* http://tools.ietf.org/html/rfc2898 (Specification)
* http://tools.ietf.org/html/rfc6070 (Test vectors)
*/
#include "polarssl/config.h"
#if defined(POLARSSL_PKCS5_C)
#include "polarssl/pkcs5.h"
#include "polarssl/asn1.h"
#include "polarssl/cipher.h"
#define OID_CMP(oid_str, oid_buf) \
( ( OID_SIZE(oid_str) == (oid_buf)->len ) && \
memcmp( (oid_str), (oid_buf)->p, (oid_buf)->len) == 0)
static int pkcs5_parse_pbkdf2_params( unsigned char **p,
const unsigned char *end,
asn1_buf *salt, int *iterations,
int *keylen, md_type_t *md_type )
{
int ret;
size_t len = 0;
asn1_buf prf_alg_oid;
/*
* PBKDF2-params ::= SEQUENCE {
* salt OCTET STRING,
* iterationCount INTEGER,
* keyLength INTEGER OPTIONAL
* prf AlgorithmIdentifier DEFAULT algid-hmacWithSHA1
* }
*
*/
if( ( ret = asn1_get_tag( p, end, &len,
ASN1_CONSTRUCTED | ASN1_SEQUENCE ) ) != 0 )
{
return( POLARSSL_ERR_PKCS5_INVALID_FORMAT + ret );
}
end = *p + len;
if( ( ret = asn1_get_tag( p, end, &salt->len, ASN1_OCTET_STRING ) ) != 0 )
return( POLARSSL_ERR_PKCS5_INVALID_FORMAT + ret );
salt->p = *p;
*p += salt->len;
if( ( ret = asn1_get_int( p, end, iterations ) ) != 0 )
return( POLARSSL_ERR_PKCS5_INVALID_FORMAT + ret );
if( *p == end )
return( 0 );
if( ( ret = asn1_get_int( p, end, keylen ) ) != 0 )
{
if( ret != POLARSSL_ERR_ASN1_UNEXPECTED_TAG )
return( POLARSSL_ERR_PKCS5_INVALID_FORMAT + ret );
}
if( *p == end )
return( 0 );
if( ( ret = asn1_get_tag( p, end, &prf_alg_oid.len, ASN1_OID ) ) != 0 )
return( POLARSSL_ERR_PKCS5_INVALID_FORMAT + ret );
if( !OID_CMP( OID_HMAC_SHA1, &prf_alg_oid ) )
return( POLARSSL_ERR_PKCS5_FEATURE_UNAVAILABLE );
*md_type = POLARSSL_MD_SHA1;
if( *p != end )
return( POLARSSL_ERR_PKCS5_INVALID_FORMAT +
POLARSSL_ERR_ASN1_LENGTH_MISMATCH );
return( 0 );
}
int pkcs5_pbes2( asn1_buf *pbe_params, int mode,
const unsigned char *pwd, size_t pwdlen,
const unsigned char *data, size_t datalen,
unsigned char *output )
{
int ret, iterations = 0, keylen = 0;
unsigned char *p, *end, *end2;
asn1_buf kdf_alg_oid, enc_scheme_oid, salt;
md_type_t md_type = POLARSSL_MD_SHA1;
unsigned char key[32], iv[32];
size_t len = 0, olen = 0;
const md_info_t *md_info;
const cipher_info_t *cipher_info;
md_context_t md_ctx;
cipher_context_t cipher_ctx;
p = pbe_params->p;
end = p + pbe_params->len;
/*
* PBES2-params ::= SEQUENCE {
* keyDerivationFunc AlgorithmIdentifier {{PBES2-KDFs}},
* encryptionScheme AlgorithmIdentifier {{PBES2-Encs}}
* }
*/
if( ( ret = asn1_get_tag( &p, end, &len,
ASN1_CONSTRUCTED | ASN1_SEQUENCE ) ) != 0 )
{
return( POLARSSL_ERR_PKCS5_INVALID_FORMAT + ret );
}
if( ( ret = asn1_get_tag( &p, end, &len,
ASN1_CONSTRUCTED | ASN1_SEQUENCE ) ) != 0 )
{
return( POLARSSL_ERR_PKCS5_INVALID_FORMAT + ret );
}
end2 = p + len;
if( ( ret = asn1_get_tag( &p, end2, &kdf_alg_oid.len, ASN1_OID ) ) != 0 )
return( POLARSSL_ERR_PKCS5_INVALID_FORMAT + ret );
kdf_alg_oid.p = p;
p += kdf_alg_oid.len;
// Only PBKDF2 supported at the moment
//
if( !OID_CMP( OID_PKCS5_PBKDF2, &kdf_alg_oid ) )
return( POLARSSL_ERR_PKCS5_FEATURE_UNAVAILABLE );
if( ( ret = pkcs5_parse_pbkdf2_params( &p, end2,
&salt, &iterations, &keylen,
&md_type ) ) != 0 )
{
return( ret );
}
md_info = md_info_from_type( md_type );
if( md_info == NULL )
return( POLARSSL_ERR_PKCS5_FEATURE_UNAVAILABLE );
if( ( ret = asn1_get_tag( &p, end, &len,
ASN1_CONSTRUCTED | ASN1_SEQUENCE ) ) != 0 )
{
return( POLARSSL_ERR_PKCS5_INVALID_FORMAT + ret );
}
end2 = p + len;
if( ( ret = asn1_get_tag( &p, end2, &enc_scheme_oid.len, ASN1_OID ) ) != 0 )
return( POLARSSL_ERR_PKCS5_INVALID_FORMAT + ret );
enc_scheme_oid.p = p;
p += enc_scheme_oid.len;
#if defined(POLARSSL_DES_C)
// Only DES-CBC and DES-EDE3-CBC supported at the moment
//
if( OID_CMP( OID_DES_EDE3_CBC, &enc_scheme_oid ) )
{
cipher_info = cipher_info_from_type( POLARSSL_CIPHER_DES_EDE3_CBC );
}
else if( OID_CMP( OID_DES_CBC, &enc_scheme_oid ) )
{
cipher_info = cipher_info_from_type( POLARSSL_CIPHER_DES_CBC );
}
else
#endif /* POLARSSL_DES_C */
return( POLARSSL_ERR_PKCS5_FEATURE_UNAVAILABLE );
if( cipher_info == NULL )
return( POLARSSL_ERR_PKCS5_FEATURE_UNAVAILABLE );
keylen = cipher_info->key_length / 8;
if( ( ret = asn1_get_tag( &p, end2, &len, ASN1_OCTET_STRING ) ) != 0 )
return( POLARSSL_ERR_PKCS5_INVALID_FORMAT + ret );
if( len != cipher_info->iv_size )
return( POLARSSL_ERR_PKCS5_INVALID_FORMAT );
memcpy( iv, p, len );
if( ( ret = md_init_ctx( &md_ctx, md_info ) ) != 0 )
return( ret );
if( ( ret = cipher_init_ctx( &cipher_ctx, cipher_info ) ) != 0 )
return( ret );
if ( ( ret = pkcs5_pbkdf2_hmac( &md_ctx, pwd, pwdlen, salt.p, salt.len,
iterations, keylen, key ) ) != 0 )
{
return( ret );
}
if( ( ret = cipher_setkey( &cipher_ctx, key, keylen, mode ) ) != 0 )
return( ret );
if( ( ret = cipher_reset( &cipher_ctx, iv ) ) != 0 )
return( ret );
if( ( ret = cipher_update( &cipher_ctx, data, datalen,
output, &olen ) ) != 0 )
{
return( ret );
}
if( ( ret = cipher_finish( &cipher_ctx, output + olen, &olen ) ) != 0 )
return( POLARSSL_ERR_PKCS5_PASSWORD_MISMATCH );
return( 0 );
}
int pkcs5_pbkdf2_hmac( md_context_t *ctx, const unsigned char *password,
size_t plen, const unsigned char *salt, size_t slen,
unsigned int iteration_count,
uint32_t key_length, unsigned char *output )
{
int ret, j;
unsigned int i;
unsigned char md1[POLARSSL_MD_MAX_SIZE];
unsigned char work[POLARSSL_MD_MAX_SIZE];
unsigned char md_size = md_get_size( ctx->md_info );
size_t use_len;
unsigned char *out_p = output;
unsigned char counter[4];
memset( counter, 0, 4 );
counter[3] = 1;
if( iteration_count > 0xFFFFFFFF )
return( POLARSSL_ERR_PKCS5_BAD_INPUT_DATA );
while( key_length )
{
// U1 ends up in work
//
if( ( ret = md_hmac_starts( ctx, password, plen ) ) != 0 )
return( ret );
if( ( ret = md_hmac_update( ctx, salt, slen ) ) != 0 )
return( ret );
if( ( ret = md_hmac_update( ctx, counter, 4 ) ) != 0 )
return( ret );
if( ( ret = md_hmac_finish( ctx, work ) ) != 0 )
return( ret );
memcpy( md1, work, md_size );
for ( i = 1; i < iteration_count; i++ )
{
// U2 ends up in md1
//
if( ( ret = md_hmac_starts( ctx, password, plen ) ) != 0 )
return( ret );
if( ( ret = md_hmac_update( ctx, md1, md_size ) ) != 0 )
return( ret );
if( ( ret = md_hmac_finish( ctx, md1 ) ) != 0 )
return( ret );
// U1 xor U2
//
for( j = 0; j < md_size; j++ )
work[j] ^= md1[j];
}
use_len = ( key_length < md_size ) ? key_length : md_size;
memcpy( out_p, work, use_len );
key_length -= use_len;
out_p += use_len;
for( i = 4; i > 0; i-- )
if( ++counter[i - 1] != 0 )
break;
}
return( 0 );
}
#if defined(POLARSSL_SELF_TEST)
#include <stdio.h>
#define MAX_TESTS 6
size_t plen[MAX_TESTS] =
{ 8, 8, 8, 8, 24, 9 };
unsigned char password[MAX_TESTS][32] =
{
"password",
"password",
"password",
"password",
"passwordPASSWORDpassword",
"pass\0word",
};
size_t slen[MAX_TESTS] =
{ 4, 4, 4, 4, 36, 5 };
unsigned char salt[MAX_TESTS][40] =
{
"salt",
"salt",
"salt",
"salt",
"saltSALTsaltSALTsaltSALTsaltSALTsalt",
"sa\0lt",
};
uint32_t it_cnt[MAX_TESTS] =
{ 1, 2, 4096, 16777216, 4096, 4096 };
uint32_t key_len[MAX_TESTS] =
{ 20, 20, 20, 20, 25, 16 };
unsigned char result_key[MAX_TESTS][32] =
{
{ 0x0c, 0x60, 0xc8, 0x0f, 0x96, 0x1f, 0x0e, 0x71,
0xf3, 0xa9, 0xb5, 0x24, 0xaf, 0x60, 0x12, 0x06,
0x2f, 0xe0, 0x37, 0xa6 },
{ 0xea, 0x6c, 0x01, 0x4d, 0xc7, 0x2d, 0x6f, 0x8c,
0xcd, 0x1e, 0xd9, 0x2a, 0xce, 0x1d, 0x41, 0xf0,
0xd8, 0xde, 0x89, 0x57 },
{ 0x4b, 0x00, 0x79, 0x01, 0xb7, 0x65, 0x48, 0x9a,
0xbe, 0xad, 0x49, 0xd9, 0x26, 0xf7, 0x21, 0xd0,
0x65, 0xa4, 0x29, 0xc1 },
{ 0xee, 0xfe, 0x3d, 0x61, 0xcd, 0x4d, 0xa4, 0xe4,
0xe9, 0x94, 0x5b, 0x3d, 0x6b, 0xa2, 0x15, 0x8c,
0x26, 0x34, 0xe9, 0x84 },
{ 0x3d, 0x2e, 0xec, 0x4f, 0xe4, 0x1c, 0x84, 0x9b,
0x80, 0xc8, 0xd8, 0x36, 0x62, 0xc0, 0xe4, 0x4a,
0x8b, 0x29, 0x1a, 0x96, 0x4c, 0xf2, 0xf0, 0x70,
0x38 },
{ 0x56, 0xfa, 0x6a, 0xa7, 0x55, 0x48, 0x09, 0x9d,
0xcc, 0x37, 0xd7, 0xf0, 0x34, 0x25, 0xe0, 0xc3 },
};
int pkcs5_self_test( int verbose )
{
md_context_t sha1_ctx;
const md_info_t *info_sha1;
int ret, i;
unsigned char key[64];
info_sha1 = md_info_from_type( POLARSSL_MD_SHA1 );
if( info_sha1 == NULL )
return( 1 );
if( ( ret = md_init_ctx( &sha1_ctx, info_sha1 ) ) != 0 )
return( 1 );
for( i = 0; i < MAX_TESTS; i++ )
{
printf( " PBKDF2 (SHA1) #%d: ", i );
ret = pkcs5_pbkdf2_hmac( &sha1_ctx, password[i], plen[i], salt[i],
slen[i], it_cnt[i], key_len[i], key );
if( ret != 0 ||
memcmp( result_key[i], key, key_len[i] ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( verbose != 0 )
printf( "passed\n" );
}
printf( "\n" );
return( 0 );
}
#endif /* POLARSSL_SELF_TEST */
#endif /* POLARSSL_PKCS5_C */
-221
View File
@@ -1,221 +0,0 @@
/*
* SSL session cache implementation
*
* Copyright (C) 2006-2012, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*
* These session callbacks use a simple chained list
* to store and retrieve the session information.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_SSL_CACHE_C)
#include "polarssl/ssl_cache.h"
#include <stdlib.h>
void ssl_cache_init( ssl_cache_context *cache )
{
memset( cache, 0, sizeof( ssl_cache_context ) );
cache->timeout = SSL_CACHE_DEFAULT_TIMEOUT;
cache->max_entries = SSL_CACHE_DEFAULT_MAX_ENTRIES;
}
int ssl_cache_get( void *data, ssl_session *session )
{
time_t t = time( NULL );
ssl_cache_context *cache = (ssl_cache_context *) data;
ssl_cache_entry *cur, *entry;
cur = cache->chain;
entry = NULL;
while( cur != NULL )
{
entry = cur;
cur = cur->next;
if( cache->timeout != 0 &&
(int) ( t - entry->timestamp ) > cache->timeout )
continue;
if( session->ciphersuite != entry->session.ciphersuite ||
session->compression != entry->session.compression ||
session->length != entry->session.length )
continue;
if( memcmp( session->id, entry->session.id,
entry->session.length ) != 0 )
continue;
memcpy( session->master, entry->session.master, 48 );
/*
* Restore peer certificate (without rest of the original chain)
*/
if( entry->peer_cert.p != NULL )
{
session->peer_cert = (x509_cert *) malloc( sizeof(x509_cert) );
if( session->peer_cert == NULL )
return( 1 );
memset( session->peer_cert, 0, sizeof(x509_cert) );
if( x509parse_crt( session->peer_cert, entry->peer_cert.p,
entry->peer_cert.len ) != 0 )
{
free( session->peer_cert );
session->peer_cert = NULL;
return( 1 );
}
}
return( 0 );
}
return( 1 );
}
int ssl_cache_set( void *data, const ssl_session *session )
{
time_t t = time( NULL ), oldest = 0;
ssl_cache_context *cache = (ssl_cache_context *) data;
ssl_cache_entry *cur, *prv, *old = NULL;
int count = 0;
cur = cache->chain;
prv = NULL;
while( cur != NULL )
{
count++;
if( cache->timeout != 0 &&
(int) ( t - cur->timestamp ) > cache->timeout )
{
cur->timestamp = t;
break; /* expired, reuse this slot, update timestamp */
}
if( memcmp( session->id, cur->session.id, cur->session.length ) == 0 )
break; /* client reconnected, keep timestamp for session id */
if( oldest == 0 || cur->timestamp < oldest )
{
oldest = cur->timestamp;
old = cur;
}
prv = cur;
cur = cur->next;
}
if( cur == NULL )
{
/*
* Reuse oldest entry if max_entries reached
*/
if( old != NULL && count >= cache->max_entries )
{
cur = old;
memset( &cur->session, 0, sizeof(ssl_session) );
if( cur->peer_cert.p != NULL )
{
free( cur->peer_cert.p );
memset( &cur->peer_cert, 0, sizeof(x509_buf) );
}
}
else
{
cur = (ssl_cache_entry *) malloc( sizeof(ssl_cache_entry) );
if( cur == NULL )
return( 1 );
memset( cur, 0, sizeof(ssl_cache_entry) );
if( prv == NULL )
cache->chain = cur;
else
prv->next = cur;
}
cur->timestamp = t;
}
memcpy( &cur->session, session, sizeof( ssl_session ) );
/*
* Store peer certificate
*/
if( session->peer_cert != NULL )
{
cur->peer_cert.p = (unsigned char *) malloc( session->peer_cert->raw.len );
if( cur->peer_cert.p == NULL )
return( 1 );
memcpy( cur->peer_cert.p, session->peer_cert->raw.p,
session->peer_cert->raw.len );
cur->peer_cert.len = session->peer_cert->raw.len;
cur->session.peer_cert = NULL;
}
return( 0 );
}
void ssl_cache_set_timeout( ssl_cache_context *cache, int timeout )
{
if( timeout < 0 ) timeout = 0;
cache->timeout = timeout;
}
void ssl_cache_set_max_entries( ssl_cache_context *cache, int max )
{
if( max < 0 ) max = 0;
cache->max_entries = max;
}
void ssl_cache_free( ssl_cache_context *cache )
{
ssl_cache_entry *cur, *prv;
cur = cache->chain;
while( cur != NULL )
{
prv = cur;
cur = cur->next;
ssl_session_free( &prv->session );
if( prv->peer_cert.p != NULL )
free( prv->peer_cert.p );
free( prv );
}
}
#endif /* POLARSSL_SSL_CACHE_C */
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
-312
View File
@@ -1,312 +0,0 @@
/*
* Portable interface to the CPU cycle counter
*
* Copyright (C) 2006-2010, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_TIMING_C)
#include "polarssl/timing.h"
#if defined(_WIN32)
#include <windows.h>
#include <winbase.h>
struct _hr_time
{
LARGE_INTEGER start;
};
#else
#include <unistd.h>
#include <sys/types.h>
#include <sys/time.h>
#include <signal.h>
#include <time.h>
struct _hr_time
{
struct timeval start;
};
#endif
#if !defined(POLARSSL_HAVE_HARDCLOCK) && defined(POLARSSL_HAVE_ASM) && \
(defined(_MSC_VER) && defined(_M_IX86)) || defined(__WATCOMC__)
#define POLARSSL_HAVE_HARDCLOCK
unsigned long hardclock( void )
{
unsigned long tsc;
__asm rdtsc
__asm mov [tsc], eax
return( tsc );
}
#endif
#if !defined(POLARSSL_HAVE_HARDCLOCK) && defined(POLARSSL_HAVE_ASM) && \
defined(__GNUC__) && defined(__i386__)
#define POLARSSL_HAVE_HARDCLOCK
unsigned long hardclock( void )
{
unsigned long lo, hi;
asm( "rdtsc" : "=a" (lo), "=d" (hi) );
return( lo );
}
#endif
#if !defined(POLARSSL_HAVE_HARDCLOCK) && defined(POLARSSL_HAVE_ASM) && \
defined(__GNUC__) && (defined(__amd64__) || defined(__x86_64__))
#define POLARSSL_HAVE_HARDCLOCK
unsigned long hardclock( void )
{
unsigned long lo, hi;
asm( "rdtsc" : "=a" (lo), "=d" (hi) );
return( lo | (hi << 32) );
}
#endif
#if !defined(POLARSSL_HAVE_HARDCLOCK) && defined(POLARSSL_HAVE_ASM) && \
defined(__GNUC__) && (defined(__powerpc__) || defined(__ppc__))
#define POLARSSL_HAVE_HARDCLOCK
unsigned long hardclock( void )
{
unsigned long tbl, tbu0, tbu1;
do
{
asm( "mftbu %0" : "=r" (tbu0) );
asm( "mftb %0" : "=r" (tbl ) );
asm( "mftbu %0" : "=r" (tbu1) );
}
while( tbu0 != tbu1 );
return( tbl );
}
#endif
#if !defined(POLARSSL_HAVE_HARDCLOCK) && defined(POLARSSL_HAVE_ASM) && \
defined(__GNUC__) && defined(__sparc64__)
#if defined(__OpenBSD__)
#warning OpenBSD does not allow access to tick register using software version instead
#else
#define POLARSSL_HAVE_HARDCLOCK
unsigned long hardclock( void )
{
unsigned long tick;
asm( "rdpr %%tick, %0;" : "=&r" (tick) );
return( tick );
}
#endif
#endif
#if !defined(POLARSSL_HAVE_HARDCLOCK) && defined(POLARSSL_HAVE_ASM) && \
defined(__GNUC__) && defined(__sparc__) && !defined(__sparc64__)
#define POLARSSL_HAVE_HARDCLOCK
unsigned long hardclock( void )
{
unsigned long tick;
asm( ".byte 0x83, 0x41, 0x00, 0x00" );
asm( "mov %%g1, %0" : "=r" (tick) );
return( tick );
}
#endif
#if !defined(POLARSSL_HAVE_HARDCLOCK) && defined(POLARSSL_HAVE_ASM) && \
defined(__GNUC__) && defined(__alpha__)
#define POLARSSL_HAVE_HARDCLOCK
unsigned long hardclock( void )
{
unsigned long cc;
asm( "rpcc %0" : "=r" (cc) );
return( cc & 0xFFFFFFFF );
}
#endif
#if !defined(POLARSSL_HAVE_HARDCLOCK) && defined(POLARSSL_HAVE_ASM) && \
defined(__GNUC__) && defined(__ia64__)
#define POLARSSL_HAVE_HARDCLOCK
unsigned long hardclock( void )
{
unsigned long itc;
asm( "mov %0 = ar.itc" : "=r" (itc) );
return( itc );
}
#endif
#if !defined(POLARSSL_HAVE_HARDCLOCK) && defined(_MSC_VER)
#define POLARSSL_HAVE_HARDCLOCK
unsigned long hardclock( void )
{
LARGE_INTEGER offset;
QueryPerformanceCounter( &offset );
return (unsigned long)( offset.QuadPart );
}
#endif
#if !defined(POLARSSL_HAVE_HARDCLOCK)
#define POLARSSL_HAVE_HARDCLOCK
static int hardclock_init = 0;
static struct timeval tv_init;
unsigned long hardclock( void )
{
struct timeval tv_cur;
if( hardclock_init == 0 )
{
gettimeofday( &tv_init, NULL );
hardclock_init = 1;
}
gettimeofday( &tv_cur, NULL );
return( ( tv_cur.tv_sec - tv_init.tv_sec ) * 1000000
+ ( tv_cur.tv_usec - tv_init.tv_usec ) );
}
#endif
volatile int alarmed = 0;
#if defined(_WIN32)
unsigned long get_timer( struct hr_time *val, int reset )
{
unsigned long delta;
LARGE_INTEGER offset, hfreq;
struct _hr_time *t = (struct _hr_time *) val;
QueryPerformanceCounter( &offset );
QueryPerformanceFrequency( &hfreq );
delta = (unsigned long)( ( 1000 *
( offset.QuadPart - t->start.QuadPart ) ) /
hfreq.QuadPart );
if( reset )
QueryPerformanceCounter( &t->start );
return( delta );
}
DWORD WINAPI TimerProc( LPVOID uElapse )
{
Sleep( (DWORD) uElapse );
alarmed = 1;
return( TRUE );
}
void set_alarm( int seconds )
{
DWORD ThreadId;
alarmed = 0;
CloseHandle( CreateThread( NULL, 0, TimerProc,
(LPVOID) ( seconds * 1000 ), 0, &ThreadId ) );
}
void m_sleep( int milliseconds )
{
Sleep( milliseconds );
}
#else
unsigned long get_timer( struct hr_time *val, int reset )
{
unsigned long delta;
struct timeval offset;
struct _hr_time *t = (struct _hr_time *) val;
gettimeofday( &offset, NULL );
delta = ( offset.tv_sec - t->start.tv_sec ) * 1000
+ ( offset.tv_usec - t->start.tv_usec ) / 1000;
if( reset )
{
t->start.tv_sec = offset.tv_sec;
t->start.tv_usec = offset.tv_usec;
}
return( delta );
}
#if defined(INTEGRITY)
void m_sleep( int milliseconds )
{
usleep( milliseconds * 1000 );
}
#else
static void sighandler( int signum )
{
alarmed = 1;
signal( signum, sighandler );
}
void set_alarm( int seconds )
{
alarmed = 0;
signal( SIGALRM, sighandler );
alarm( seconds );
}
void m_sleep( int milliseconds )
{
struct timeval tv;
tv.tv_sec = milliseconds / 1000;
tv.tv_usec = milliseconds * 1000;
select( 0, NULL, NULL, NULL, &tv );
}
#endif /* INTEGRITY */
#endif
#endif
-50
View File
@@ -1,50 +0,0 @@
/*
* Version information
*
* Copyright (C) 2006-2010, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_VERSION_C)
#include "polarssl/version.h"
#include <string.h>
const char version[] = POLARSSL_VERSION_STRING;
unsigned int version_get_number()
{
return POLARSSL_VERSION_NUMBER;
}
void version_get_string( char *string )
{
memcpy( string, POLARSSL_VERSION_STRING, sizeof( POLARSSL_VERSION_STRING ) );
}
void version_get_string_full( char *string )
{
memcpy( string, POLARSSL_VERSION_STRING_FULL, sizeof( POLARSSL_VERSION_STRING_FULL ) );
}
#endif /* POLARSSL_VERSION_C */
File diff suppressed because it is too large Load Diff
-285
View File
@@ -1,285 +0,0 @@
/*
* X509 buffer writing functionality
*
* Copyright (C) 2006-2012, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_X509_WRITE_C)
#include "polarssl/asn1write.h"
#include "polarssl/x509write.h"
#include "polarssl/x509.h"
#include "polarssl/sha1.h"
#include "polarssl/sha2.h"
#include "polarssl/sha4.h"
#include "polarssl/md4.h"
#include "polarssl/md5.h"
int x509_write_pubkey_der( unsigned char *buf, size_t size, rsa_context *rsa )
{
int ret;
unsigned char *c;
size_t len = 0;
c = buf + size - 1;
ASN1_CHK_ADD( len, asn1_write_mpi( &c, buf, &rsa->E ) );
ASN1_CHK_ADD( len, asn1_write_mpi( &c, buf, &rsa->N ) );
ASN1_CHK_ADD( len, asn1_write_len( &c, buf, len ) );
ASN1_CHK_ADD( len, asn1_write_tag( &c, buf, ASN1_CONSTRUCTED | ASN1_SEQUENCE ) );
if( c - buf < 1 )
return( POLARSSL_ERR_ASN1_BUF_TOO_SMALL );
*--c = 0;
len += 1;
ASN1_CHK_ADD( len, asn1_write_len( &c, buf, len ) );
ASN1_CHK_ADD( len, asn1_write_tag( &c, buf, ASN1_BIT_STRING ) );
ASN1_CHK_ADD( len, asn1_write_algorithm_identifier( &c, buf, OID_PKCS1_RSA ) );
ASN1_CHK_ADD( len, asn1_write_len( &c, buf, len ) );
ASN1_CHK_ADD( len, asn1_write_tag( &c, buf, ASN1_CONSTRUCTED | ASN1_SEQUENCE ) );
return( len );
}
int x509_write_key_der( unsigned char *buf, size_t size, rsa_context *rsa )
{
int ret;
unsigned char *c;
size_t len = 0;
c = buf + size - 1;
ASN1_CHK_ADD( len, asn1_write_mpi( &c, buf, &rsa->QP ) );
ASN1_CHK_ADD( len, asn1_write_mpi( &c, buf, &rsa->DQ ) );
ASN1_CHK_ADD( len, asn1_write_mpi( &c, buf, &rsa->DP ) );
ASN1_CHK_ADD( len, asn1_write_mpi( &c, buf, &rsa->Q ) );
ASN1_CHK_ADD( len, asn1_write_mpi( &c, buf, &rsa->P ) );
ASN1_CHK_ADD( len, asn1_write_mpi( &c, buf, &rsa->D ) );
ASN1_CHK_ADD( len, asn1_write_mpi( &c, buf, &rsa->E ) );
ASN1_CHK_ADD( len, asn1_write_mpi( &c, buf, &rsa->N ) );
ASN1_CHK_ADD( len, asn1_write_int( &c, buf, 0 ) );
ASN1_CHK_ADD( len, asn1_write_len( &c, buf, len ) );
ASN1_CHK_ADD( len, asn1_write_tag( &c, buf, ASN1_CONSTRUCTED | ASN1_SEQUENCE ) );
// TODO: Make NON RSA Specific variant later on
/* *--c = 0;
len += 1;
len += asn1_write_len( &c, len);
len += asn1_write_tag( &c, ASN1_BIT_STRING );
len += asn1_write_oid( &c, OID_PKCS1_RSA );
len += asn1_write_int( &c, 0 );
len += asn1_write_len( &c, len);
len += asn1_write_tag( &c, ASN1_CONSTRUCTED | ASN1_SEQUENCE );*/
/* for(i = 0; i < len; ++i)
{
if (i % 16 == 0 ) printf("\n");
printf("%02x ", c[i]);
}
printf("\n");*/
return( len );
}
int x509_write_name( unsigned char **p, unsigned char *start, char *oid,
char *name )
{
int ret;
size_t string_len = 0;
size_t oid_len = 0;
size_t len = 0;
// Write PrintableString for all except OID_PKCS9_EMAIL
//
if( OID_SIZE( OID_PKCS9_EMAIL ) == strlen( oid ) &&
memcmp( oid, OID_PKCS9_EMAIL, strlen( oid ) ) == 0 )
{
ASN1_CHK_ADD( string_len, asn1_write_ia5_string( p, start, name ) );
}
else
ASN1_CHK_ADD( string_len, asn1_write_printable_string( p, start, name ) );
// Write OID
//
ASN1_CHK_ADD( oid_len, asn1_write_oid( p, start, oid ) );
len = oid_len + string_len;
ASN1_CHK_ADD( len, asn1_write_len( p, start, oid_len + string_len ) );
ASN1_CHK_ADD( len, asn1_write_tag( p, start, ASN1_CONSTRUCTED | ASN1_SEQUENCE ) );
ASN1_CHK_ADD( len, asn1_write_len( p, start, len ) );
ASN1_CHK_ADD( len, asn1_write_tag( p, start, ASN1_CONSTRUCTED | ASN1_SET ) );
return( len );
}
/*
* Wrapper for x509 hashes.
*/
static void x509_hash( const unsigned char *in, size_t len, int alg,
unsigned char *out )
{
switch( alg )
{
#if defined(POLARSSL_MD2_C)
case SIG_RSA_MD2 : md2( in, len, out ); break;
#endif
#if defined(POLARSSL_MD4_C)
case SIG_RSA_MD4 : md4( in, len, out ); break;
#endif
#if defined(POLARSSL_MD5_C)
case SIG_RSA_MD5 : md5( in, len, out ); break;
#endif
#if defined(POLARSSL_SHA1_C)
case SIG_RSA_SHA1 : sha1( in, len, out ); break;
#endif
#if defined(POLARSSL_SHA2_C)
case SIG_RSA_SHA224 : sha2( in, len, out, 1 ); break;
case SIG_RSA_SHA256 : sha2( in, len, out, 0 ); break;
#endif
#if defined(POLARSSL_SHA4_C)
case SIG_RSA_SHA384 : sha4( in, len, out, 1 ); break;
case SIG_RSA_SHA512 : sha4( in, len, out, 0 ); break;
#endif
default:
memset( out, '\xFF', 64 );
break;
}
}
int x509_write_sig( unsigned char **p, unsigned char *start, char *oid,
unsigned char *sig, size_t size )
{
int ret;
size_t len = 0;
if( *p - start < (int) size + 1 )
return( POLARSSL_ERR_ASN1_BUF_TOO_SMALL );
len = size;
(*p) -= len;
memcpy( *p, sig, len );
*--(*p) = 0;
len += 1;
ASN1_CHK_ADD( len, asn1_write_len( p, start, len ) );
ASN1_CHK_ADD( len, asn1_write_tag( p, start, ASN1_BIT_STRING ) );
// Write OID
//
ASN1_CHK_ADD( len, asn1_write_algorithm_identifier( p, start, oid ) );
return( len );
}
int x509_write_cert_req( unsigned char *buf, size_t size, rsa_context *rsa,
x509_req_name *req_name, int hash_id )
{
int ret;
char sig_oid[10];
unsigned char *c, *c2;
unsigned char hash[64];
unsigned char sig[POLARSSL_MPI_MAX_SIZE];
unsigned char tmp_buf[2048];
size_t sub_len = 0, pub_len = 0, sig_len = 0;
size_t len = 0;
x509_req_name *cur = req_name;
c = tmp_buf + 2048 - 1;
ASN1_CHK_ADD( len, asn1_write_len( &c, tmp_buf, 0 ) );
ASN1_CHK_ADD( len, asn1_write_tag( &c, tmp_buf, ASN1_CONSTRUCTED | ASN1_CONTEXT_SPECIFIC ) );
ASN1_CHK_ADD( pub_len, asn1_write_mpi( &c, tmp_buf, &rsa->E ) );
ASN1_CHK_ADD( pub_len, asn1_write_mpi( &c, tmp_buf, &rsa->N ) );
ASN1_CHK_ADD( pub_len, asn1_write_len( &c, tmp_buf, pub_len ) );
ASN1_CHK_ADD( pub_len, asn1_write_tag( &c, tmp_buf, ASN1_CONSTRUCTED | ASN1_SEQUENCE ) );
if( c - tmp_buf < 1 )
return( POLARSSL_ERR_ASN1_BUF_TOO_SMALL );
*--c = 0;
pub_len += 1;
ASN1_CHK_ADD( pub_len, asn1_write_len( &c, tmp_buf, pub_len ) );
ASN1_CHK_ADD( pub_len, asn1_write_tag( &c, tmp_buf, ASN1_BIT_STRING ) );
ASN1_CHK_ADD( pub_len, asn1_write_algorithm_identifier( &c, tmp_buf, OID_PKCS1_RSA ) );
len += pub_len;
ASN1_CHK_ADD( len, asn1_write_len( &c, tmp_buf, pub_len ) );
ASN1_CHK_ADD( len, asn1_write_tag( &c, tmp_buf, ASN1_CONSTRUCTED | ASN1_SEQUENCE ) );
while( cur != NULL )
{
ASN1_CHK_ADD( sub_len, x509_write_name( &c, tmp_buf, cur->oid, cur->name ) );
cur = cur->next;
}
len += sub_len;
ASN1_CHK_ADD( len, asn1_write_len( &c, tmp_buf, sub_len ) );
ASN1_CHK_ADD( len, asn1_write_tag( &c, tmp_buf, ASN1_CONSTRUCTED | ASN1_SEQUENCE ) );
ASN1_CHK_ADD( len, asn1_write_int( &c, tmp_buf, 0 ) );
ASN1_CHK_ADD( len, asn1_write_len( &c, tmp_buf, len ) );
ASN1_CHK_ADD( len, asn1_write_tag( &c, tmp_buf, ASN1_CONSTRUCTED | ASN1_SEQUENCE ) );
x509_hash( c, len, hash_id, hash );
rsa_pkcs1_sign( rsa, NULL, NULL, RSA_PRIVATE, hash_id, 0, hash, sig );
// Generate correct OID
//
memcpy( sig_oid, OID_PKCS1, 8 );
sig_oid[8] = hash_id;
sig_oid[9] = '\0';
c2 = buf + size - 1;
ASN1_CHK_ADD( sig_len, x509_write_sig( &c2, buf, sig_oid, sig, rsa->len ) );
c2 -= len;
memcpy( c2, c, len );
len += sig_len;
ASN1_CHK_ADD( len, asn1_write_len( &c2, buf, len ) );
ASN1_CHK_ADD( len, asn1_write_tag( &c2, buf, ASN1_CONSTRUCTED | ASN1_SEQUENCE ) );
return( len );
}
#endif
-251
View File
@@ -1,251 +0,0 @@
/*
* An 32-bit implementation of the XTEA algorithm
*
* Copyright (C) 2006-2013, Brainspark B.V.
*
* This file is part of PolarSSL (http://www.polarssl.org)
* Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
*
* All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "polarssl/config.h"
#if defined(POLARSSL_XTEA_C)
#include "polarssl/xtea.h"
#if !defined(POLARSSL_XTEA_ALT)
/*
* 32-bit integer manipulation macros (big endian)
*/
#ifndef GET_UINT32_BE
#define GET_UINT32_BE(n,b,i) \
{ \
(n) = ( (uint32_t) (b)[(i) ] << 24 ) \
| ( (uint32_t) (b)[(i) + 1] << 16 ) \
| ( (uint32_t) (b)[(i) + 2] << 8 ) \
| ( (uint32_t) (b)[(i) + 3] ); \
}
#endif
#ifndef PUT_UINT32_BE
#define PUT_UINT32_BE(n,b,i) \
{ \
(b)[(i) ] = (unsigned char) ( (n) >> 24 ); \
(b)[(i) + 1] = (unsigned char) ( (n) >> 16 ); \
(b)[(i) + 2] = (unsigned char) ( (n) >> 8 ); \
(b)[(i) + 3] = (unsigned char) ( (n) ); \
}
#endif
/*
* XTEA key schedule
*/
void xtea_setup( xtea_context *ctx, unsigned char key[16] )
{
int i;
memset(ctx, 0, sizeof(xtea_context));
for( i = 0; i < 4; i++ )
{
GET_UINT32_BE( ctx->k[i], key, i << 2 );
}
}
/*
* XTEA encrypt function
*/
int xtea_crypt_ecb( xtea_context *ctx, int mode, unsigned char input[8],
unsigned char output[8])
{
uint32_t *k, v0, v1, i;
k = ctx->k;
GET_UINT32_BE( v0, input, 0 );
GET_UINT32_BE( v1, input, 4 );
if( mode == XTEA_ENCRYPT )
{
uint32_t sum = 0, delta = 0x9E3779B9;
for( i = 0; i < 32; i++ )
{
v0 += (((v1 << 4) ^ (v1 >> 5)) + v1) ^ (sum + k[sum & 3]);
sum += delta;
v1 += (((v0 << 4) ^ (v0 >> 5)) + v0) ^ (sum + k[(sum>>11) & 3]);
}
}
else /* XTEA_DECRYPT */
{
uint32_t delta = 0x9E3779B9, sum = delta * 32;
for( i = 0; i < 32; i++ )
{
v1 -= (((v0 << 4) ^ (v0 >> 5)) + v0) ^ (sum + k[(sum>>11) & 3]);
sum -= delta;
v0 -= (((v1 << 4) ^ (v1 >> 5)) + v1) ^ (sum + k[sum & 3]);
}
}
PUT_UINT32_BE( v0, output, 0 );
PUT_UINT32_BE( v1, output, 4 );
return( 0 );
}
/*
* XTEA-CBC buffer encryption/decryption
*/
int xtea_crypt_cbc( xtea_context *ctx,
int mode,
size_t length,
unsigned char iv[8],
unsigned char *input,
unsigned char *output)
{
int i;
unsigned char temp[8];
if(length % 8)
return( POLARSSL_ERR_XTEA_INVALID_INPUT_LENGTH );
if( mode == XTEA_DECRYPT )
{
while( length > 0 )
{
memcpy( temp, input, 8 );
xtea_crypt_ecb( ctx, mode, input, output );
for(i = 0; i < 8; i++)
output[i] = (unsigned char)( output[i] ^ iv[i] );
memcpy( iv, temp, 8 );
input += 8;
output += 8;
length -= 8;
}
}
else
{
while( length > 0 )
{
for( i = 0; i < 8; i++ )
output[i] = (unsigned char)( input[i] ^ iv[i] );
xtea_crypt_ecb( ctx, mode, output, output );
memcpy( iv, output, 8 );
input += 8;
output += 8;
length -= 8;
}
}
return( 0 );
}
#endif /* !POLARSSL_XTEA_ALT */
#if defined(POLARSSL_SELF_TEST)
#include <string.h>
#include <stdio.h>
/*
* XTEA tests vectors (non-official)
*/
static const unsigned char xtea_test_key[6][16] =
{
{ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b,
0x0c, 0x0d, 0x0e, 0x0f },
{ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b,
0x0c, 0x0d, 0x0e, 0x0f },
{ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b,
0x0c, 0x0d, 0x0e, 0x0f },
{ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00 },
{ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00 },
{ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00 }
};
static const unsigned char xtea_test_pt[6][8] =
{
{ 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48 },
{ 0x41, 0x41, 0x41, 0x41, 0x41, 0x41, 0x41, 0x41 },
{ 0x5a, 0x5b, 0x6e, 0x27, 0x89, 0x48, 0xd7, 0x7f },
{ 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48 },
{ 0x41, 0x41, 0x41, 0x41, 0x41, 0x41, 0x41, 0x41 },
{ 0x70, 0xe1, 0x22, 0x5d, 0x6e, 0x4e, 0x76, 0x55 }
};
static const unsigned char xtea_test_ct[6][8] =
{
{ 0x49, 0x7d, 0xf3, 0xd0, 0x72, 0x61, 0x2c, 0xb5 },
{ 0xe7, 0x8f, 0x2d, 0x13, 0x74, 0x43, 0x41, 0xd8 },
{ 0x41, 0x41, 0x41, 0x41, 0x41, 0x41, 0x41, 0x41 },
{ 0xa0, 0x39, 0x05, 0x89, 0xf8, 0xb8, 0xef, 0xa5 },
{ 0xed, 0x23, 0x37, 0x5a, 0x82, 0x1a, 0x8c, 0x2d },
{ 0x41, 0x41, 0x41, 0x41, 0x41, 0x41, 0x41, 0x41 }
};
/*
* Checkup routine
*/
int xtea_self_test( int verbose )
{
int i;
unsigned char buf[8];
xtea_context ctx;
for( i = 0; i < 6; i++ )
{
if( verbose != 0 )
printf( " XTEA test #%d: ", i + 1 );
memcpy( buf, xtea_test_pt[i], 8 );
xtea_setup( &ctx, (unsigned char *) xtea_test_key[i] );
xtea_crypt_ecb( &ctx, XTEA_ENCRYPT, buf, buf );
if( memcmp( buf, xtea_test_ct[i], 8 ) != 0 )
{
if( verbose != 0 )
printf( "failed\n" );
return( 1 );
}
if( verbose != 0 )
printf( "passed\n" );
}
if( verbose != 0 )
printf( "\n" );
return( 0 );
}
#endif
#endif
+29
View File
@@ -0,0 +1,29 @@
========================================================================
MAKEFILE PROJECT : makerom Project Overview
========================================================================
AppWizard has created this makerom project for you.
This file contains a summary of what you will find in each of the files that
make up your makerom project.
makerom.vcxproj
This is the main project file for VC++ projects generated using an Application Wizard.
It contains information about the version of Visual C++ that generated the file, and
information about the platforms, configurations, and project features selected with the
Application Wizard.
makerom.vcxproj.filters
This is the filters file for VC++ projects generated using an Application Wizard.
It contains information about the association between the files in your project
and the filters. This association is used in the IDE to show grouping of files with
similar extensions under a specific node (for e.g. ".cpp" files are associated with the
"Source Files" filter).
This project allows you to build/clean/rebuild from within Visual Studio by calling the commands you have input
in the wizard. The build command can be nmake or any other tool you use.
This project does not contain any files, so there are none displayed in Solution Explorer.
/////////////////////////////////////////////////////////////////////////////
+8 -19
View File
@@ -54,7 +54,7 @@ typedef struct
u8 siblingoffset[4];
u8 childoffset[4];
u8 fileoffset[4];
u8 weirdoffset[4]; // this one is weird. it always points to a dir entry, but seems unrelated to the romfs structure.
u8 hashoffset[4];
u8 namesize[4];
//u8 name[ROMFS_MAXNAMESIZE];
} romfs_direntry; //sizeof(romfs_direntry) = 0x18
@@ -65,7 +65,7 @@ typedef struct
u8 siblingoffset[4];
u8 dataoffset[8];
u8 datasize[8];
u8 weirdoffset[4]; // this one is also weird. it always points to a file entry, but seems unrelated to the romfs structure.
u8 hashoffset[4];
u8 namesize[4];
//u8 name[ROMFS_MAXNAMESIZE];
} romfs_fileentry; //sizeof(romfs_fileentry) = 0x20
@@ -86,18 +86,18 @@ typedef struct
fs_dir *fs;
u32 *dirUTable;
u32 m_dirUTableEntry;
u32 u_dirUTableEntry;
u32 *dirHashTable;
u32 m_dirHashTable;
u32 u_dirHashTable;
u8 *dirTable;
u32 dirNum;
u32 m_dirTableLen;
u32 u_dirTableLen;
u32 *fileUTable;
u32 m_fileUTableEntry;
u32 u_fileUTableEntry;
u32 *fileHashTable;
u32 m_fileHashTable;
u32 u_fileHashTable;
u8 *fileTable;
u32 fileNum;
@@ -112,16 +112,5 @@ typedef struct
ivfc_level level[4];
} romfs_buildctx;
/*
typedef struct
{
u8 *output;
u64 romfsSize;
u64 romfsHeaderSize;
bool ImportRomfsBinary;
FILE *romfsBinary;
} romfs_buildctx;
*/
int SetupRomFs(ncch_settings *ncchset, romfs_buildctx *ctx);
int BuildRomFs(romfs_buildctx *ctx);
+156 -173
View File
@@ -11,11 +11,13 @@ const fs_romfs_char ROMFS_EMPTY_PATH[2] = {0x0000, 0x0000};
bool IsFileWanted(fs_file *file, void *filter_criteria);
bool IsDirWanted(fs_dir *dir, void *filter_criteria);
void CalcDirSize(romfs_buildctx *ctx, fs_dir *fs);
int CalcRomfsSize(romfs_buildctx *ctx);
int AddFileToRomfs(romfs_buildctx *ctx, fs_file *file, u32 parent, u32 sibling);
int AddDirToRomfs(romfs_buildctx *ctx, fs_dir *fs, u32 parent, u32 sibling);
void CalcRomfsSize(romfs_buildctx *ctx);
int FilterRomFS(fs_dir *fs_raw, fs_dir *fs_filtered, void *filter_criteria);
int PopulateRomfs(romfs_buildctx *ctx);
void AddFileToRomfs(romfs_buildctx *ctx, fs_file *file, u32 parent, u32 sibling);
void AddDirToRomfs(romfs_buildctx *ctx, fs_dir *fs, u32 parent, u32 sibling);
void AddDirChildrenToRomfs(romfs_buildctx *ctx, fs_dir *fs, u32 parent, u32 dir);
void PopulateHashTable(romfs_buildctx *ctx);
void PopulateRomfs(romfs_buildctx *ctx);
void BuildRomfsHeader(romfs_buildctx *ctx);
void BuildIvfcHeader(romfs_buildctx *ctx);
void GenIvfcHashTree(romfs_buildctx *ctx);
@@ -24,9 +26,7 @@ u32 CalcPathHash(u32 parent, fs_romfs_char* path, u32 start, u32 length);
int PrepareBuildRomFsBinary(ncch_settings *ncchset, romfs_buildctx *ctx)
{
// Input Path
//printf("Get input path\n");
/* Input Path */
const int CWD_MAX_LEN = 1024;
char *cwd = calloc(CWD_MAX_LEN,sizeof(char));
getcwd(cwd,CWD_MAX_LEN);
@@ -44,45 +44,33 @@ int PrepareBuildRomFsBinary(ncch_settings *ncchset, romfs_buildctx *ctx)
fs_path = dir;
#endif
// FS Structures
/* FS Structures */
void *filter_criteria = NULL;
//printf("calloc fs_raw\n");
fs_dir *fs_raw = calloc(1,sizeof(fs_dir));
//printf("calloc ctx->fs\n");
ctx->fs = calloc(1,sizeof(fs_dir));
//memdump(stdout,"ctx->fs: ",(u8*)ctx->fs,sizeof(fs_dir));
//printf("ctx->fs = 0x%x\n",ctx->fs);
// Import FS and process
//printf("open fs into fs_raw\n");
/* Import FS and process */
fs_OpenDir(fs_path,path,path_len,fs_raw);
//printf("filter fs_raw into ctx->fs\n");
FilterRomFS(fs_raw,ctx->fs,filter_criteria);
// free unfiltered FS
//fs_PrintDir(fs_raw,0);
//printf("free discarded file ptrs\n");
/* free unfiltered FS */
fs_FreeFiles(fs_raw); // All important FPs have been moved with FilterRomFS, so only un-wanted FPs are closed here
//printf("free structs in fs_raw\n");
fs_FreeDir(fs_raw);
//printf("free fs_raw\n");
free(fs_raw);
//printf("leave if no ROMFS needs to be made\n");
if(ctx->fs->u_file == 0){
/* Abort romfs making, if no wanted files/directories were found */
if(ctx->fs->u_file == 0 && ctx->fs->u_dir == 0){
ctx->romfsSize = 0;
goto finish;
}
// Print Filtered FS
//printf("print filtered FS\n");
/* Print Filtered FS */
if(ncchset->options.verbose){
printf("[ROMFS] File System:\n");
fs_PrintDir(ctx->fs,0);
}
//printf("predict romfs size\n");
CalcRomfsSize(ctx);
finish:
@@ -92,13 +80,13 @@ finish:
int BuildRomFsBinary(romfs_buildctx *ctx)
{
// Decide IVFC Level Actual Offsets
/* Decide IVFC Level Actual Offsets */
ctx->level[0].offset = 0;
ctx->level[3].offset = ctx->level[0].offset + align(ctx->level[0].size, ROMFS_BLOCK_SIZE);
ctx->level[1].offset = ctx->level[3].offset + align(ctx->level[3].size, ROMFS_BLOCK_SIZE);
ctx->level[2].offset = ctx->level[1].offset + align(ctx->level[1].size, ROMFS_BLOCK_SIZE);
// Decide IVFC Level Logical Offsets
/* Decide IVFC Level Logical Offsets */
for(int i = 1; i < 4; i++){
if(i == 1)
ctx->level[i].logicalOffset = 0;
@@ -106,21 +94,20 @@ int BuildRomFsBinary(romfs_buildctx *ctx)
ctx->level[i].logicalOffset = align(ctx->level[i-1].logicalOffset + ctx->level[i-1].size,ROMFS_BLOCK_SIZE);
}
// Setup IVFC Level Ptrs
/* Setup IVFC Level Ptrs */
for(int i = 0; i < 4; i++){
ctx->level[i].pos = (ctx->output + ctx->level[i].offset);
if(i == 0)
ctx->level[i].pos += align(sizeof(ivfc_hdr),0x10);
}
// Build Romfs
/* Build Romfs */
ctx->romfsHdr = (romfs_infoheader*)(ctx->level[3].pos);
BuildRomfsHeader(ctx);
if(PopulateRomfs(ctx) != 0)
return -1;
PopulateRomfs(ctx);
// Finalise by building IVFC hash tree
/* Finalise by building IVFC hash tree */
ctx->ivfcHdr = (ivfc_hdr*)(ctx->output + ctx->level[0].offset);
BuildIvfcHeader(ctx);
GenIvfcHashTree(ctx);
@@ -180,27 +167,33 @@ void CalcDirSize(romfs_buildctx *ctx, fs_dir *fs)
ctx->dirNum += fs->u_dir;
}
int CalcRomfsSize(romfs_buildctx *ctx)
u32 GetHashTableCount(u32 num)
{
u32 count = num;
if (num < 3)
count = 3;
else if (count < 19)
count |= 1;
else {
while (count % 2 == 0 || count % 3 == 0 || count % 5 == 0 || count % 7 == 0 || count % 11 == 0 || count % 13 == 0 || count % 17 == 0)
count++;
}
return count;
}
void CalcRomfsSize(romfs_buildctx *ctx)
{
ctx->dirNum = 1; // root dir
//printf("Recursively get FS sizes\n");
CalcDirSize(ctx,ctx->fs);
//printf("check U tables\n");
ctx->u_dirUTableEntry = 0;
ctx->m_dirUTableEntry = 3;
if(ctx->dirNum > 3)
ctx->m_dirUTableEntry += align(ctx->dirNum-3,2);
ctx->u_dirHashTable = 0;
ctx->m_dirHashTable = GetHashTableCount(ctx->dirNum);
ctx->u_fileUTableEntry = 0;
ctx->m_fileUTableEntry = 3;
if(ctx->fileNum > 3)
ctx->m_fileUTableEntry += align(ctx->fileNum-3,2);
ctx->u_fileHashTable = 0;
ctx->m_fileHashTable = GetHashTableCount(ctx->fileNum);
//printf("calc romfs header size\n");
u32 romfsHdrSize = align(sizeof(romfs_infoheader) + ctx->m_dirUTableEntry*sizeof(u32) + ctx->m_dirTableLen + ctx->m_fileUTableEntry*sizeof(u32) + ctx->m_fileTableLen,0x10);
u32 romfsHdrSize = align(sizeof(romfs_infoheader) + ctx->m_dirHashTable*sizeof(u32) + ctx->m_dirTableLen + ctx->m_fileHashTable*sizeof(u32) + ctx->m_fileTableLen,0x10);
//printf("predict level sizes\n");
ctx->level[3].size = romfsHdrSize + ctx->m_dataLen; // data
ctx->level[2].size = align(ctx->level[3].size,ROMFS_BLOCK_SIZE) / ROMFS_BLOCK_SIZE * SHA_256_LEN ;
ctx->level[1].size = align(ctx->level[2].size,ROMFS_BLOCK_SIZE) / ROMFS_BLOCK_SIZE * SHA_256_LEN ;
@@ -208,13 +201,9 @@ int CalcRomfsSize(romfs_buildctx *ctx)
ctx->romfsHeaderSize = ctx->level[0].size;
//printf("calc total ROMFS size\n");
ctx->romfsSize = 0;
for(int i = 0; i < 4; i++)
ctx->romfsSize += align(ctx->level[i].size,ROMFS_BLOCK_SIZE);
//printf("return from CalcRomfsSize();\n");
return 0;
ctx->romfsSize += align(ctx->level[i].size,ROMFS_BLOCK_SIZE);
}
int FilterRomFS(fs_dir *fs_raw, fs_dir *fs_filtered, void *filter_criteria)
@@ -278,10 +267,10 @@ void BuildRomfsHeader(romfs_buildctx *ctx)
for(int i = 0; i < 4; i++){
if(i == 0){
ctx->dirUTable = (u32*)(ctx->level[3].pos + level3_pos);
ctx->dirHashTable = (u32*)(ctx->level[3].pos + level3_pos);
u32_to_u8(ctx->romfsHdr->section[i].offset,level3_pos,LE);
u32_to_u8(ctx->romfsHdr->section[i].size,ctx->m_dirUTableEntry*sizeof(u32),LE);
level3_pos += ctx->m_dirUTableEntry*sizeof(u32);
u32_to_u8(ctx->romfsHdr->section[i].size,ctx->m_dirHashTable*sizeof(u32),LE);
level3_pos += ctx->m_dirHashTable*sizeof(u32);
}
else if(i == 1 && ctx->m_dirTableLen){
ctx->dirTable = ctx->level[3].pos + level3_pos;
@@ -290,10 +279,10 @@ void BuildRomfsHeader(romfs_buildctx *ctx)
level3_pos += ctx->m_dirTableLen;
}
else if(i == 2){
ctx->fileUTable = (u32*)(ctx->level[3].pos + level3_pos);
ctx->fileHashTable = (u32*)(ctx->level[3].pos + level3_pos);
u32_to_u8(ctx->romfsHdr->section[i].offset,level3_pos,LE);
u32_to_u8(ctx->romfsHdr->section[i].size,ctx->m_fileUTableEntry*sizeof(u32),LE);
level3_pos += ctx->m_fileUTableEntry*sizeof(u32);
u32_to_u8(ctx->romfsHdr->section[i].size,ctx->m_fileHashTable*sizeof(u32),LE);
level3_pos += ctx->m_fileHashTable*sizeof(u32);
}
else if(i == 3 && ctx->m_fileTableLen){
ctx->fileTable = ctx->level[3].pos + level3_pos;
@@ -310,73 +299,47 @@ void BuildRomfsHeader(romfs_buildctx *ctx)
ctx->data = ctx->level[3].pos + align(level3_pos,0x10);
u32_to_u8(ctx->romfsHdr->dataoffset,align(level3_pos,0x10),LE);
memset(ctx->dirUTable,0xff,ctx->m_dirUTableEntry*sizeof(u32));
memset(ctx->fileUTable,0xff,ctx->m_fileUTableEntry*sizeof(u32));
return;
}
for (u32 i = 0; i < ctx->m_dirHashTable; i++) {
ctx->dirHashTable[i] = ROMFS_UNUSED_ENTRY;
}
void AddDirHashKey(romfs_buildctx *ctx, u32 parent, fs_romfs_char* path, u32 dirOffset)
{
u32 hash = CalcPathHash(parent,path,0,fs_u16StrLen(path));
u32 index = hash % ctx->m_dirUTableEntry;
if(ctx->dirUTable[index] == ROMFS_UNUSED_ENTRY) ctx->dirUTable[index] = dirOffset;
else
{
romfs_direntry * curdir = (romfs_direntry*)(ctx->dirTable + ctx->dirUTable[index]);
while(1)
{
if(*(u32*)curdir->weirdoffset == ROMFS_UNUSED_ENTRY)
{
*(u32*)curdir->weirdoffset = dirOffset;
break;
}
else
{
curdir = (romfs_direntry*)(ctx->dirTable + *(u32*)curdir->weirdoffset);
}
}
for (u32 i = 0; i < ctx->m_fileHashTable; i++) {
ctx->fileHashTable[i] = ROMFS_UNUSED_ENTRY;
}
}
void AddFileHashKey(romfs_buildctx *ctx,u32 parent, fs_romfs_char *path, u32 fileOffset)
u32 GetFileHashTableIndex(romfs_buildctx *ctx, u32 parent, fs_romfs_char *path)
{
u32 hash = CalcPathHash(parent,path,0,fs_u16StrLen(path));
u32 index = hash % ctx->m_fileUTableEntry;
if(ctx->fileUTable[index] == ROMFS_UNUSED_ENTRY) ctx->fileUTable[index] = fileOffset;
else
{
romfs_fileentry * curfile = (romfs_fileentry*)(ctx->fileTable + ctx->fileUTable[index]);
while(1)
{
if(*(u32*)curfile->weirdoffset == ROMFS_UNUSED_ENTRY)
{
*(u32*)curfile->weirdoffset = fileOffset;
break;
}
else
{
curfile = (romfs_fileentry*)(ctx->fileTable + *(u32*)curfile->weirdoffset);
}
}
}
u32 hash = CalcPathHash(parent, path, 0, fs_u16StrLen(path));
return hash % ctx->m_fileHashTable;
}
int AddFileToRomfs(romfs_buildctx *ctx, fs_file *file, u32 parent, u32 sibling)
u32 GetDirHashTableIndex(romfs_buildctx *ctx, u32 parent, fs_romfs_char* path)
{
u32 hash = CalcPathHash(parent, path, 0, fs_u16StrLen(path));
return hash % ctx->m_dirHashTable;
}
void AddFileToRomfs(romfs_buildctx *ctx, fs_file *file, u32 parent, u32 sibling)
{
romfs_fileentry *entry = (romfs_fileentry*)(ctx->fileTable + ctx->u_fileTableLen);
u32_to_u8(entry->parentdiroffset,parent,LE);
u32_to_u8(entry->siblingoffset,sibling,LE);
u32_to_u8(entry->weirdoffset,ROMFS_UNUSED_ENTRY,LE);
// Import Name
/* Import name */
u32_to_u8(entry->namesize,file->name_len,LE);
u8 *name_pos = (u8*)(ctx->fileTable + ctx->u_fileTableLen + sizeof(romfs_fileentry));
memset(name_pos,0,align(file->name_len,4));
memcpy(name_pos,(u8*)file->name,file->name_len);
/* Set hash data */
u32 hashindex = GetFileHashTableIndex(ctx, parent, file->name);
u32_to_u8(entry->hashoffset, ctx->fileHashTable[hashindex], LE);
ctx->fileHashTable[hashindex] = ctx->u_fileTableLen;
// Import Data
/* Import data */
if(file->size)
{
ctx->u_dataLen = align(ctx->u_dataLen,0x10); // Padding
@@ -387,98 +350,118 @@ int AddFileToRomfs(romfs_buildctx *ctx, fs_file *file, u32 parent, u32 sibling)
ctx->u_dataLen += file->size; // adding file size
}
else
u64_to_u8(entry->dataoffset,0x40,LE);
u64_to_u8(entry->dataoffset,0x00,LE);
AddFileHashKey(ctx,parent,file->name,ctx->u_fileTableLen);
/* Increment used file table length */
ctx->u_fileTableLen += sizeof(romfs_fileentry) + align(file->name_len,4);
return 0;
}
int AddDirToRomfs(romfs_buildctx *ctx, fs_dir *fs, u32 parent, u32 sibling)
void AddDirToRomfs(romfs_buildctx *ctx, fs_dir *fs, u32 parent, u32 sibling)
{
//wprintf(L"adding %s \n",fs->name);
romfs_direntry *entry = (romfs_direntry*)(ctx->dirTable + ctx->u_dirTableLen);
u32 offset = ctx->u_dirTableLen;
u32 hashindex;
romfs_direntry *entry = (romfs_direntry*)(ctx->dirTable + offset);
/* Set entry data */
u32_to_u8(entry->parentoffset,parent,LE);
u32_to_u8(entry->siblingoffset,sibling,LE);
u32_to_u8(entry->weirdoffset,ROMFS_UNUSED_ENTRY,LE);
u32 Currentdir = ctx->u_dirTableLen;
u32_to_u8(entry->childoffset, ROMFS_UNUSED_ENTRY, LE);
u32_to_u8(entry->fileoffset, ROMFS_UNUSED_ENTRY, LE);
if(Currentdir == 0)
/* If root dir ... */
if(offset == 0)
{
/* Import name (root dir has no name) */
u32_to_u8(entry->namesize,0,LE);
AddDirHashKey(ctx,parent,(fs_romfs_char*)ROMFS_EMPTY_PATH,ctx->u_dirTableLen);
/* Get hash table index */
hashindex = GetFileHashTableIndex(ctx, parent, (fs_romfs_char*)ROMFS_EMPTY_PATH);
/* Increment used dir table length */
ctx->u_dirTableLen += sizeof(romfs_direntry);
}
else
{
/* Import name */
u32_to_u8(entry->namesize,fs->name_len,LE);
u8 *name_pos = (u8*)(ctx->dirTable + ctx->u_dirTableLen + sizeof(romfs_direntry));
memset(name_pos,0,(u32)align(fs->name_len,4));
memcpy(name_pos,(u8*)fs->name,fs->name_len);
AddDirHashKey(ctx,parent,fs->name,ctx->u_dirTableLen);
/* Get hash table index */
hashindex = GetFileHashTableIndex(ctx, parent, fs->name);
/* Increment used dir table length */
ctx->u_dirTableLen += sizeof(romfs_direntry) + (u32)align(fs->name_len,4);
}
if(fs->u_file)
{
u32_to_u8(entry->fileoffset,ctx->u_fileTableLen,LE);
for(u32 i = 0; i < fs->u_file; i++)
{
u32 file_sibling = 0;
if(i >= fs->u_file-1)
file_sibling = ROMFS_UNUSED_ENTRY;
else
file_sibling = ctx->u_fileTableLen + sizeof(romfs_fileentry) + (u32)align(fs->file[i].name_len,4);
//wprintf(L"adding %s (0x%lx)\n",fs->file[i].name,fs->file[i].size);
AddFileToRomfs(ctx,&fs->file[i],Currentdir,file_sibling);
//wprintf(L"added %s (0x%lx)\n",fs->file[i].name,fs->file[i].size);
}
}
else
u32_to_u8(entry->fileoffset,ROMFS_UNUSED_ENTRY,LE);
//printf("Checking if to add dirs\n");
if(fs->u_dir)
{
//printf(" is adding dirs \n");
u32_to_u8(entry->childoffset,ctx->u_dirTableLen,LE);
fs_dir *dir = (fs_dir*)fs->dir;
for(u32 i = 0; i < fs->u_dir; i++)
{
u32 dir_sibling = 0;
romfs_direntry *temp_entry = (romfs_direntry*)(ctx->dirTable + ctx->u_dirTableLen);
if(i >= fs->u_dir-1)
dir_sibling = ROMFS_UNUSED_ENTRY;
else
{
//printf(" dir has sibling\n");
dir_sibling = ctx->u_dirTableLen + sizeof(romfs_direntry) + (u32)align(dir[i].name_len,4);
}
AddDirToRomfs(ctx,&dir[i],Currentdir,dir_sibling);
if(dir_sibling != ROMFS_UNUSED_ENTRY)
{
dir_sibling = ctx->u_dirTableLen;//修复同目录文件夹偏移 (Repair the same directory folder offset)
u32_to_u8(temp_entry->siblingoffset,dir_sibling,LE);
}
}
}
else
u32_to_u8(entry->childoffset,ROMFS_UNUSED_ENTRY,LE);
//printf(" finished adding dirs \n");
//wprintf(L"added %s \n",fs->name);
return 0;
/* Set hash data */
u32_to_u8(entry->hashoffset, ctx->dirHashTable[hashindex], LE);
ctx->dirHashTable[hashindex] = offset;
}
int PopulateRomfs(romfs_buildctx *ctx)
void AddDirChildrenToRomfs(romfs_buildctx *ctx, fs_dir *fs, u32 parent, u32 dir)
{
return AddDirToRomfs(ctx,ctx->fs,0x0,ROMFS_UNUSED_ENTRY);
romfs_direntry *entry = (romfs_direntry*)(ctx->dirTable + dir);
if (fs->u_file)
{
u32_to_u8(entry->fileoffset, ctx->u_fileTableLen, LE);
/* Create file entries*/
for (u32 i = 0; i < fs->u_file; i++)
{
/* If is the last file, no more siblings */
u32 file_sibling = 0;
if (i >= fs->u_file - 1)
file_sibling = ROMFS_UNUSED_ENTRY;
else
file_sibling = ctx->u_fileTableLen + sizeof(romfs_fileentry) + (u32)align(fs->file[i].name_len, 4);
/* Create file entry */
AddFileToRomfs(ctx, &fs->file[i], dir, file_sibling);
}
}
if (fs->u_dir)
{
/* Prepare to store child addresses */
u32 *childs = calloc(fs->u_dir, sizeof(u32));
/* Create child directory entries*/
u32_to_u8(entry->childoffset, ctx->u_dirTableLen, LE);
fs_dir *subdir = (fs_dir*)fs->dir;
for (u32 i = 0; i < fs->u_dir; i++)
{
/* Store address fo child */
childs[i] = ctx->u_dirTableLen;
u32 dir_sibling = 0;
if (i >= fs->u_dir - 1)
dir_sibling = ROMFS_UNUSED_ENTRY;
else
dir_sibling = ctx->u_dirTableLen + sizeof(romfs_direntry) + (u32)align(subdir[i].name_len, 4);
/* Create child directory entry */
AddDirToRomfs(ctx, &subdir[i], dir, dir_sibling);
}
/* Populate child's childs */
for (u32 i = 0; i < fs->u_dir; i++)
{
AddDirChildrenToRomfs(ctx, &subdir[i], dir, childs[i]);
}
free(childs);
}
}
void PopulateRomfs(romfs_buildctx *ctx)
{
AddDirToRomfs(ctx, ctx->fs, 0x0, ROMFS_UNUSED_ENTRY);
AddDirChildrenToRomfs(ctx, ctx->fs, 0x0, 0);
}
void BuildIvfcHeader(romfs_buildctx *ctx)
+10 -2
View File
@@ -102,12 +102,16 @@ void GET_AccessControlInfo(ctr_yaml_context *ctx, rsf_settings *rsf)
else if(cmpYamlValue("UseOtherVariationSaveData",ctx)) SetBoolYAMLValue(&rsf->AccessControlInfo.UseOtherVariationSaveData,"UseOtherVariationSaveData",ctx);
else if(cmpYamlValue("RunnableOnSleep",ctx)) SetBoolYAMLValue(&rsf->AccessControlInfo.RunnableOnSleep,"RunnableOnSleep",ctx);
else if(cmpYamlValue("SpecialMemoryArrange",ctx)) SetBoolYAMLValue(&rsf->AccessControlInfo.SpecialMemoryArrange,"SpecialMemoryArrange",ctx);
else if(cmpYamlValue("UseExtSaveData", ctx)) SetBoolYAMLValue(&rsf->AccessControlInfo.UseExtSaveData, "UseExtSaveData", ctx);
else if(cmpYamlValue("EnableL2Cache", ctx)) SetBoolYAMLValue(&rsf->AccessControlInfo.EnableL2Cache, "EnableL2Cache", ctx);
else if(cmpYamlValue("IdealProcessor",ctx)) SetSimpleYAMLValue(&rsf->AccessControlInfo.IdealProcessor,"IdealProcessor",ctx,0);
else if(cmpYamlValue("Priority",ctx)) SetSimpleYAMLValue(&rsf->AccessControlInfo.Priority,"Priority",ctx,0);
else if(cmpYamlValue("MemoryType",ctx)) SetSimpleYAMLValue(&rsf->AccessControlInfo.MemoryType,"MemoryType",ctx,0);
else if(cmpYamlValue("SystemMode",ctx)) SetSimpleYAMLValue(&rsf->AccessControlInfo.SystemMode,"SystemMode",ctx,0);
else if(cmpYamlValue("SystemModeExt", ctx)) SetSimpleYAMLValue(&rsf->AccessControlInfo.SystemModeExt, "SystemModeExt", ctx, 0);
else if(cmpYamlValue("CpuSpeed", ctx)) SetSimpleYAMLValue(&rsf->AccessControlInfo.CpuSpeed, "CpuSpeed", ctx, 0);
else if(cmpYamlValue("CoreVersion",ctx)) SetSimpleYAMLValue(&rsf->AccessControlInfo.CoreVersion,"CoreVersion",ctx,0);
else if(cmpYamlValue("HandleTableSize",ctx)) SetSimpleYAMLValue(&rsf->AccessControlInfo.HandleTableSize,"HandleTableSize",ctx,0);
else if(cmpYamlValue("SystemSaveDataId1",ctx)) SetSimpleYAMLValue(&rsf->AccessControlInfo.SystemSaveDataId1,"SystemSaveDataId1",ctx,0);
@@ -279,7 +283,8 @@ void GET_TitleInfo(ctr_yaml_context *ctx, rsf_settings *rsf)
if(ctx->error || ctx->done) return;
// Handle childs
if(cmpYamlValue("Category",ctx)) SetSimpleYAMLValue(&rsf->TitleInfo.Category,"Category",ctx,0);
if (cmpYamlValue("Platform", ctx)) SetSimpleYAMLValue(&rsf->TitleInfo.Platform, "Platform", ctx, 0);
else if(cmpYamlValue("Category",ctx)) SetSimpleYAMLValue(&rsf->TitleInfo.Category,"Category",ctx,0);
else if(cmpYamlValue("UniqueId",ctx)) SetSimpleYAMLValue(&rsf->TitleInfo.UniqueId,"UniqueId",ctx,0);
else if(cmpYamlValue("Version",ctx)) SetSimpleYAMLValue(&rsf->TitleInfo.Version,"Version",ctx,0);
else if(cmpYamlValue("ContentsIndex",ctx)) SetSimpleYAMLValue(&rsf->TitleInfo.ContentsIndex,"ContentsIndex",ctx,0);
@@ -382,6 +387,8 @@ void free_RsfSettings(rsf_settings *set)
free(set->AccessControlInfo.Priority);
free(set->AccessControlInfo.MemoryType);
free(set->AccessControlInfo.SystemMode);
free(set->AccessControlInfo.SystemModeExt);
free(set->AccessControlInfo.CpuSpeed);
free(set->AccessControlInfo.CoreVersion);
free(set->AccessControlInfo.HandleTableSize);
free(set->AccessControlInfo.SystemSaveDataId1);
@@ -502,6 +509,7 @@ void free_RsfSettings(rsf_settings *set)
free(set->PlainRegion);
//TitleInfo
free(set->TitleInfo.Platform);
free(set->TitleInfo.Category);
free(set->TitleInfo.UniqueId);
free(set->TitleInfo.Version);
+6 -1
View File
@@ -86,12 +86,16 @@ typedef struct
bool UseOtherVariationSaveData;
bool RunnableOnSleep;
bool SpecialMemoryArrange;
bool UseExtSaveData;
bool EnableL2Cache;
// Strings
char *IdealProcessor;
char *Priority;
char *MemoryType;
char *SystemMode;
char *SystemModeExt;
char *CpuSpeed;
char *CoreVersion;
char *HandleTableSize;
char *SystemSaveDataId1;
@@ -178,6 +182,7 @@ typedef struct
struct{
// Strings
char *Platform;
char *Category;
char *UniqueId;
char *Version;