Reputation: 1166
I'm writing a code to find a proper input that would generate a certain output for the SHA-1 hash function.
The problem I'm running into is that my code raises a segmentation fault, but gdb
finds that it raises the following error upon entering main()
and befor execution of any other code:
Program received signal SIGSEGV, Segmentation fault.
__strncpy_sse2_unaligned () at ../sysdeps/x86_64/multiarch/strcpy-sse2-unaligned.S:636
636 ../sysdeps/x86_64/multiarch/strcpy-sse2-unaligned.S: No such file or directory.
This is my code:
#include <iostream>
#include <cstdlib>
#include <cstring>
#include "sha1.hpp"
int main() {
char *prefix = "SHA1sha1";
char *suffix = "chicken and beer";
std::string hashvalue = "nonzero";
char *line = "just some dummy string";
int loop_number = 0;
while (hashvalue.c_str()[0] != '0' || hashvalue.c_str()[1] != '0') {
// change prefix
strncpy(prefix, hashvalue.c_str(), 8);
// hash the concatenated string of prefix and suffix
strncpy(line, prefix, 8);
strncat(line, suffix, strlen(suffix));
hashvalue = sha1(line);
loop_number++;
if (loop_number % 1000 == 0) std::cout << loop_number << "th loop, hash value: " << hashvalue << std::endl;
}
std::cout << "Found prefix: " << prefix << " with hash value: " << hashvalue << std::endl;
return 0;
}
The sha1.hpp
was not implemented by me, but was taken from here: http://www.zedwood.com/article/cpp-sha1-function
I have changed sha1.h
to sha1.hpp
, though, but this is probably not what's causing the segmentation fault.
Now I have tried searching for a solution to this problem with the error message and also with the keywords "segmentation fault before main", and this post seems to be going through similar problems: Segmentation Fault before main
However, I have looked into the two suggested solutions, but couldn't find one that fits me.
I don't think my code has too many variables in the stack. In fact, I have tried commenting out using the function sha1()
just in case, but the same problem occurred.
I have initialized all char*
and std::string
in my code before usage.
FYI, I'm using g++
to compile my C++ codes.
Any help or push in the right direction would be greatly appreciated.
Upvotes: 3
Views: 305
Reputation: 12732
You are modifying the immutable contents.
// change prefix
strncpy(prefix, hashvalue.c_str(), 8);
// hash the concatenated string of prefix and suffix
strncpy(line, prefix, 8);
strncat(line, suffix, strlen(suffix));
Try to change the declaration as below.
char prefix[100] = "SHA1sha1";
char suffix[200] = "chicken and beer";
char line[200] = "just some dummy string
Also, I guess
while (hashvalue.c_str()[0] != '0' || hashvalue.c_str()[1] != '0') {
should be
while (hashvalue.c_str()[0] != '0' && hashvalue.c_str()[1] != '0') {
Update:
De Morgan's law states,
not (A and B) = not A or not B
Again it is individual's choice to use whatever form they want
Upvotes: 4
Reputation: 310950
String literals have types of constant character arrays in C++, and any attempt to modify a string literal results in undefined behavior. You are trying to modify a string literal at least in this statement:
strncpy(prefix, hashvalue.c_str(), 8);
Instead of string literals you should use character arrays or objects of the type std::string
.
Pay attention to that; for example this if
statement
while (hashvalue.c_str()[0] != '0' || hashvalue.c_str()[1] != '0') {
could be written much simpler:
while (hashvalue[0] != '0' || hashvalue[1] != '0') {
though it seems the condition does not make sense. Maybe you mean the following
while ( hashvalue.size() > 1 ) {
Also you need to include the header <string>
#include <string>
Upvotes: 4