简体   繁体   English

CGo 将 go 字符串转换为 *C.uchar

[英]CGo Convert go string to *C.uchar

var originalMsg *C.uchar
C.ecall_pay_w(8, 10, &originalMsg, &signature)
originalMsgStr := fmt.Sprintf("%c", originalMsg)

//Todo convert originalMstStr to same value with originalMsg

i have to convert go str(originalMsgStr) to *C.uchar type which is same value with originalMsg.我必须将 go str(originalMsgStr) 转换为与 originalMsg 值相同的 *C.uchar 类型。 How can i do it?我该怎么做?

You get a C-string back from your call to C.ecall_pay_w and want to convert that C-string to a Go-string.您从对C.ecall_pay_w的调用中得到一个 C 字符串,并希望将该 C 字符串转换为 Go 字符串。 You can do this by manually following the C-string until you reach the terminating 0 .您可以通过手动跟随 C 字符串直到到达终止0来执行此操作。

Assuming that:假如说:

  • There is a terminating 0 at the end of the C-string C 字符串的末尾有一个终止符0
  • The C-string is encoded as ASCII, so every byte represents an ASCII character (in the range [0..127]). C 字符串被编码为 ASCII,因此每个字节代表一个 ASCII 字符(在 [0..127] 范围内)。 This means it is both ASCII and UTF-8 at the same time because UTF-8 is backward compatible to ASCII.这意味着它同时是 ASCII 和 UTF-8,因为 UTF-8 向后兼容 ASCII。

Then your solution could be this:那么你的解决方案可能是这样的:

    func convertCStringToGoString(c *C.uchar) string {
        var buf []byte
        for *c != 0 {
            buf = append(buf, *c)
            c = (*C.uchar)(unsafe.Pointer(uintptr(unsafe.Pointer(c)) + 1))
        }
        return string(buf)
    }

Note that doing "unsafe" things like this in Go is cast-heavy.请注意,在 Go 中做这样的“不安全”的事情是繁重的。 That was done on purpose by the Go authors.这是 Go 作者有意完成的。 You need to convert to unsafe.Pointer before you can convert to uintptr .您需要先转换为unsafe.Pointer然后才能转换为uintptr The uintptr can be added to ( + 1 ) while the unsafe.Pointer does not support that. uintptr可以添加到 ( + 1 ) 而unsafe.Pointer不支持。 These are the reasons for that much casting.这些都是铸造那么多的原因。

I do not know Go in much detail, but do not forget that in C the *C.uchar would be something like unsigned char * which is often used to reference a string (Null-terminated array of characters).我不太了解 Go,但不要忘记在 C 中*C.uchar类似于unsigned char * ,它通常用于引用字符串(以空字符结尾的字符数组)。

Here you use fmt.Sprintf("%c", originalMsg) , with %c which expects a single char, so apart from the language detail on how you would cast the resulting string to a *C.uchar , you most probably have lost content already.在这里,您使用fmt.Sprintf("%c", originalMsg)%c这需要一个单个字符,从语言的细节,这样除了你如何将得到的字符串转换*C.uchar ,你很可能已经失去了内容已经。

%c the character represented by the corresponding Unicode code point %c 对应的Unicode码位所代表的字符

From https://golang.org/pkg/fmt/#hdr-Printing来自https://golang.org/pkg/fmt/#hdr-Printing

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM