C 写入和读取二进制文件
我试图将C 写入和读取二进制文件,c,post-quantum-cryptography,C,Post Quantum Cryptography,我试图将crypt->public\u key->data写入一个二进制文件。如果我在fwrite()中使用size ofsizeof(unsigned int)作为第二个参数,它会起作用。但是,它在头文件中声明为unsigned short*类型。我不知道它为什么会这样。此外,我在编写公钥和阅读公钥时也面临这个问题。尽管我在fwrite()和fread()中使用了完全相同类型的大小 编辑:正如usr2564301所指出的,我的密码->公钥->数据的大小似乎不正确 *我不确定是否需要引用此代码的
crypt->public\u key->data
写入一个二进制文件。如果我在fwrite()
中使用size ofsizeof(unsigned int)
作为第二个参数,它会起作用。但是,它在头文件中声明为unsigned short*
类型。我不知道它为什么会这样。此外,我在编写公钥和阅读公钥时也面临这个问题。尽管我在fwrite()
和fread()
中使用了完全相同类型的大小
编辑:正如usr2564301所指出的,我的密码->公钥->数据的大小似乎不正确
*我不确定是否需要引用此代码的源代码。但我会在这里添加URL:
来自矩阵的代码
typedef struct matrix
{
int rows; //number of rows.
int cols; //number of columns.
unsigned short *data;
}*bin_matrix;
这是来自mcelice.c的代码
//Initialize the mceliece cryptosystem
mcc mceliece_init(int n0, int p, int w, int t)
{
FILE *publicKey, *privateKey;
mcc crypt;
crypt = (mcc)safe_malloc(sizeof(struct mceliece));
//crypt->code = qc_mdpc_init(n0, p, w, t);
//crypt->public_key = generator_matrix(crypt->code);
//printf("%d\n",crypt->public_key->rows);
//printf("%d\n",crypt->public_key->cols);
//Write public key into a binary file
/*publicKey = fopen("PublicKey.bin", "wb");
privateKey = fopen("PrivateKey.bin", "wb");
if(privateKey != NULL){
fwrite(crypt->code->row, n0*p*sizeof(unsigned short), n0 * p, privateKey);
fclose(privateKey);
}
else{
printf("Unable to write private key\n");
}
//Write public key into a binary file
if(publicKey != NULL){
fwrite(crypt->public_key->data, p*p*n0*sizeof(unsigned short), crypt->public_key->rows*crypt->public_key->cols, publicKey);
fclose(publicKey);
}
else{
printf("Unable to write public key\n");
}*/
//Read private key from a binary file
crypt->code = (mdpc)safe_malloc(sizeof(struct qc_mdpc));
crypt->code->n0 = n0;
crypt->code->p = p;
crypt->code->w = w;
crypt->code->t = t;
crypt->code->n = n0 * p;
crypt->code->r = p;
crypt->code->k = (n0 - 1) * p;
crypt->code->row = (unsigned short*)calloc(n0 * p, sizeof(unsigned short));
privateKey = fopen("PrivateKey.bin", "rb");
if(privateKey != NULL){
fread(crypt->code->row, p*n0*sizeof(unsigned short), p*n0, privateKey);
fclose(privateKey);
}
else
printf("Unable to read private key\n");
//Read public key from a binary file
/*crypt->public_key = (bin_matrix)safe_malloc(sizeof(struct matrix));
crypt->public_key->data = (unsigned short*)safe_malloc(p*p*n0*sizeof(unsigned short));
crypt->public_key->rows = p;
crypt->public_key->cols = n0*p;
publicKey = fopen("PublicKey.bin", "rb");
if(publicKey != NULL){
fread(crypt->public_key->data, p*p*n0*sizeof(unsigned short), crypt->public_key->rows*crypt->public_key->cols, publicKey);
fclose(publicKey);
}
else{
printf("Unable to read public key\n");
}*/
printf("Successful\n");
//printf("mceliece generated...\n");
return crypt;
}
我们的阅读声明中存在一个混乱:
fread(crypt->code->row, p*n0*sizeof(unsigned short), p*n0, privateKey);
这将尝试读取p*n0
元素,每个元素的大小为p*n0*sizeof(无符号短)
字节。如果文件不大于分配的大小,您将很幸运,因为fread
不会尝试写入超出分配块末尾的内容
你应该写:
size_t nread = fread(crypt->code->row, sizeof(unsigned short), p * n0, privateKey);
if (nread == p * n0) {
/* private key was read successfully */
} else {
/* file is too short, only nread words were read */
}
sizeof(unsigned int)
是一个常量大小,由编译器提供。但是,您不知道->data
处的数据量是否有那么大–您无法从指针导出分配的大小。您可能需要根据该结构中的其他元素计算其实际大小。@SteveSummit:该值乘以前面的sizeof(unsigned int)
。这不可能是正确的–它可能应该是sizeof(未消化的短)
。记住,OP对什么不起作用是含糊不清的。写入的数据太少?太多?@Lance乘以sizeof(unsigned short)
应该是正确的,因为这是基础数据的大小。用sizeof(unsigned int)
相乘应该是非常错误的,并且不应该起作用。当您使用unsigned short
时,您能更清楚地说明它是如何失败的吗?crypt->public\u key->rows
和->cols
是否在调用fwrite
的位置正确设置?(可能设置它们的代码在generator\u matrix()
中)我收到一条解码失败消息,它位于qc\u mdpc.c的decode()中。我认为'crypt->public_key->rows'和'->cols'是正确的,因为我没有修改原始代码中这部分的任何内容。fread
不能保证读取请求的数据,即使文件中有那么多数据。@zwol:实际上,它是:C11 7.21.8.1p3 ` fread`函数返回成功读取的元素数,如果遇到读取错误或文件结尾,则该函数可能小于nEMB
。如果size
或nmemb
为零,fread
返回零,数组内容和流状态保持不变。您必须引用unixread
系统调用,该调用可能会由于多种原因返回短计数,即使文件中有可用数据。您的解释是合理的,但我不知道有任何fread
实现在read
返回短计数时在内部循环,所以实际上,fread
的用户必须准备好处理短读。@zwol:真的吗?我只是查了一下glibc,在内部函数\u IO\u default\u xsgetn
中找到了正确的循环。glibc是一项需要解决的工作。newlibc在内部函数\u fread\u r
中也有循环。源于BSD的Apple libc在\uuuufread
和\uuufread0
中也有适当的循环。您必须指的是古老或异国情调的实现。如果fread
在某个随机位置停止,则无法正确重新启动。有道理,它只会因为文件结束或读取错误而失败,就像getc
@Lance:您在同一台计算机上编码和解码吗?您只发布了一段代码,我无法告诉您应用程序其余部分中的错误。