首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何在Go (类型转换问题)中实现HashCash算法?

如何在Go (类型转换问题)中实现HashCash算法?
EN

Stack Overflow用户
提问于 2012-03-14 09:39:48
回答 2查看 973关注 0票数 0

我一直在尝试在Go中实现HashCash算法!对那些不知道的人来说-

HashCash是一种阻止垃圾邮件的方法。基本上,头是由客户端和服务器都知道的一些环境变量(电子邮件、时间戳等)构建的。在标头的末尾附加一个随机的nonce。客户端试图通过更改当前值来强求部分散列冲突(例如,前x位为0)。

HashCash之所以有效,是因为查找部分哈希冲突并不那么昂贵。当服务器接收到此头时,它们会验证其中的信息(因此只能用于一个会话)并计算结果哈希。如果前x位是0,那么在客户机的机器上花费了大量的时间,计算碰撞(这不会发生在垃圾邮件上)

对我来说,我只是想编写一个程序,它可以找到客户端查找x位部分散列冲突所需的时间。

我编写了这段代码,如果int64有x位的哈希冲突,它将返回true/false。

代码语言:javascript
复制
func partialAllZeroes (zeroCount uint8, val int64) (bool, os.Error) {
    setBitString := "1111111111111111111111111111111111111111111111111111111111111111"
    unsetBitString := "0000000000000000000000000000000000000000000000000000000000000000"
    setBitString = setBitString[0:zeroCount-1]
    unsetBitString = unsetBitString[0:zeroCount-1]
    
    zeroTest, e := strconv.Btoi64(setBitString, 2) // 64 0bits
    zeroes, e   := strconv.Btoi64(unsetBitString, 2) // 64 1bits
    
    if e != nil {
        return false, e
    }
    result := val & zeroTest
    switch {
        case result == zeroes:
            return true, nil
        case result != zeroes:
            return false, nil
    }
    
    return false, os.NewError("")
}

我目前的问题是,我有很多类型转换问题。例如,我只能对int64类型进行操作,因为这就是strconv.Btoi64返回的内容。另一个问题是,哈希函数作为字节数组返回,我不知道如何将其转换为int64。

下面是我现在的哈希码-

代码语言:javascript
复制
hasher := sha1.New()
baseCollisionString := "BASE COLLISION STRING"
nonce := "12345"
hasher.Write([]byte(strings.Join(baseCollisionString, nonce)))
testCollision := hasher.Sum()
// Somehow I must convert the first x bits of testCollision into an int64 type, so I can use partialAllZeroes with it
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2012-03-14 11:22:46

我建议使用以下代码(函数partialAllZeroes应该运行得更快):

代码语言:javascript
复制
package main

import "crypto/sha1"

func partialAllZeroes(zeroCount uint8, b []byte) bool {
    i := 0
    for zeroCount >= 8 {
        if b[i] != 0 {
            return false
        }
        i++
        zeroCount -= 8
    }

    var mask byte
    switch zeroCount {
    case 0: mask = 0x00
    case 1: mask = 0x01
    case 2: mask = 0x03
    case 3: mask = 0x07
    case 4: mask = 0x0f
    case 5: mask = 0x1f
    case 6: mask = 0x3f
    case 7: mask = 0x7f
    }

    return (b[i] & mask) == 0
}

func main() {
    hasher := sha1.New()
    baseCollisionString := "BASE COLLISION STRING"
    nonce := "12345"
    hasher.Write([]byte(baseCollisionString + nonce))
    testCollision := hasher.Sum()
    partialAllZeroes(100, testCollision)
}
票数 4
EN

Stack Overflow用户

发布于 2012-03-14 10:16:06

我还建议升级到最新的每周(从昨天起RC1)。"go fix“命令将帮助您进行转换。

然后使用strconv:

代码语言:javascript
复制
package main

import (
        "fmt"
        "strconv"
        "reflect"
)

func main() {
        a := []byte{ '1', '1', '1', '0', '1', '0', '1', '1' }

        b, err := strconv.ParseInt(string(a[:3]), 2, 64)
        if err != nil {
                fmt.Println(err)
                return
        }

        fmt.Println(b, reflect.TypeOf(b))
}
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/9699307

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档