Add optimized SHA-256d implementation for x86

This commit is contained in:
pooler 2012-03-31 16:44:59 +02:00
parent 7dd70bc05f
commit 9093f84686
4 changed files with 1257 additions and 40 deletions

View file

@ -15,7 +15,7 @@ bin_PROGRAMS = minerd
minerd_SOURCES = elist.h miner.h compat.h \
cpu-miner.c util.c \
sha2.c sha2-x64.S \
sha2.c sha2-x86.S sha2-x64.S \
scrypt.c scrypt-x86.S scrypt-x64.S
minerd_LDFLAGS = $(PTHREAD_FLAGS)
minerd_LDADD = @LIBCURL@ @JANSSON_LIBS@ @PTHREAD_LIBS@ @WS2_LIBS@

View file

@ -112,7 +112,7 @@ static inline void le32enc(void *pp, uint32_t x)
void sha256_init(uint32_t *state);
void sha256_transform(uint32_t *state, const uint32_t *block, int swap);
#if defined(__x86_64__)
#if defined(__i386__) || defined(__x86_64__)
#define HAVE_SHA256_4WAY 1
int sha256_use_4way();
void sha256_init_4way(uint32_t *state);

1196
sha2-x86.S Normal file

File diff suppressed because it is too large Load diff

67
sha2.c
View file

@ -418,49 +418,39 @@ static inline void sha256d_ms(uint32_t *hash, uint32_t *W,
}
#ifdef HAVE_SHA256_4WAY
#define SHA256D_MAX_WAYS 4
void sha256d_ms_4way(uint32_t *hash, uint32_t *data,
const uint32_t *midstate, const uint32_t *prehash);
#else
#define SHA256D_MAX_WAYS 1
#endif
int scanhash_sha256d(int thr_id, uint32_t *pdata, const uint32_t *ptarget,
uint32_t max_nonce, unsigned long *hashes_done)
static inline int scanhash_sha256d_4way(int thr_id, uint32_t *pdata,
const uint32_t *ptarget, uint32_t max_nonce, unsigned long *hashes_done)
{
uint32_t data[SHA256D_MAX_WAYS * 64] __attribute__((aligned(128)));
uint32_t hash[SHA256D_MAX_WAYS * 8] __attribute__((aligned(32)));
uint32_t midstate[SHA256D_MAX_WAYS * 8] __attribute__((aligned(32)));
uint32_t prehash[SHA256D_MAX_WAYS * 8] __attribute__((aligned(32)));
uint32_t data[4 * 64] __attribute__((aligned(128)));
uint32_t hash[4 * 8] __attribute__((aligned(32)));
uint32_t midstate[4 * 8] __attribute__((aligned(32)));
uint32_t prehash[4 * 8] __attribute__((aligned(32)));
uint32_t n = pdata[19] - 1;
const uint32_t first_nonce = pdata[19];
const uint32_t Htarg = ptarget[7];
#ifdef HAVE_SHA256_4WAY
const int ways = sha256_use_4way() ? 4 : 1;
#else
const int ways = 1;
#endif
int i, j;
memcpy(data, pdata + 16, 64);
sha256d_preextend(data);
for (i = 31; i >= 0; i--)
for (j = 0; j < ways; j++)
data[i * ways + j] = data[i];
for (j = 0; j < 4; j++)
data[i * 4 + j] = data[i];
sha256_init(midstate);
sha256_transform(midstate, pdata, 0);
memcpy(prehash, midstate, 32);
sha256d_prehash(prehash, pdata + 16);
for (i = 7; i >= 0; i--) {
for (j = 0; j < ways; j++) {
midstate[i * ways + j] = midstate[i];
prehash[i * ways + j] = prehash[i];
for (j = 0; j < 4; j++) {
midstate[i * 4 + j] = midstate[i];
prehash[i * 4 + j] = prehash[i];
}
}
#ifdef HAVE_SHA256_4WAY
if (ways == 4)
do {
for (i = 0; i < 4; i++)
data[4 * 3 + i] = ++n;
@ -478,8 +468,39 @@ int scanhash_sha256d(int thr_id, uint32_t *pdata, const uint32_t *ptarget,
}
}
} while (n < max_nonce && !work_restart[thr_id].restart);
else
*hashes_done = n - first_nonce + 1;
pdata[19] = n;
return 0;
}
#endif /* HAVE_SHA256_4WAY */
int scanhash_sha256d(int thr_id, uint32_t *pdata, const uint32_t *ptarget,
uint32_t max_nonce, unsigned long *hashes_done)
{
uint32_t data[64] __attribute__((aligned(128)));
uint32_t hash[8] __attribute__((aligned(32)));
uint32_t midstate[8] __attribute__((aligned(32)));
uint32_t prehash[8] __attribute__((aligned(32)));
uint32_t n = pdata[19] - 1;
const uint32_t first_nonce = pdata[19];
const uint32_t Htarg = ptarget[7];
#ifdef HAVE_SHA256_4WAY
if (sha256_use_4way())
return scanhash_sha256d_4way(thr_id, pdata, ptarget,
max_nonce, hashes_done);
#endif
memcpy(data, pdata + 16, 64);
sha256d_preextend(data);
sha256_init(midstate);
sha256_transform(midstate, pdata, 0);
memcpy(prehash, midstate, 32);
sha256d_prehash(prehash, pdata + 16);
do {
data[3] = ++n;
sha256d_ms(hash, data, midstate, prehash);