mhw0 / libethc Goto Github PK
View Code? Open in Web Editor NEWOpen-source Ethereum C library
Home Page: https://mhw0.github.io/libethc/
License: MIT License
Open-source Ethereum C library
Home Page: https://mhw0.github.io/libethc/
License: MIT License
Hello brother. When i try to get my address from PK using the below code, it returns an error of [libsecp256k1] illegal argument: secp256k1_ecmult_gen_context_is_built(&ctx->ecmult_gen_ctx)
the coed is
#include <ethc/account.h>
#include <ethc/hex.h>
#include <ethc/keccak256.h>
#include <iostream>
using namespace std;
void test_eth_account_address_get()
{
struct eth_account account;
uint8_t privkey[32] = {0xdc, 0xdf, 0x91, 0xb7, 0xb2, 0x9c, 0x4c, 0x06,
0x77, 0x33, 0x1b, 0x65, 0x5c, 0x0c, 0x6c, 0xf4,
0xe7, 0x1b, 0x6f, 0x87, 0x19, 0x27, 0x3a, 0x11,
0x2e, 0xe6, 0x5b, 0x63, 0x9b, 0x88, 0x8f, 0xfa};
char out[40];
eth_account_from_privkey(&account, privkey);
eth_account_address_get(out, &account);
cout << out << endl;
}
int main()
{
test_eth_account_address_get();
}
Hello there,
First off, absolutely amazing project. I am trying to compare the output of the library to something like eth_account for python and Web3. I found this strange offset f842a0
after signing a simple message. The full source code is given in the screenshot below. Notice I am using the private key as was given in the Examples section of the docs.
The above code, seems to return the following signature:
f842a0
40911813bd523b3dbc83f5eb06d024fb43d09609068842dba37c53527fabc33e
a0
3ec391e743b820de01600842f7b23af1b19786e5778766f7e94798bfe500807a
With input keccak hash being:
85f11dc9d9ca7c444897e464dcc1bf1b936931cba10fe3b7b4e58b516a6851a8
What I find relatively interesting is that doing the exact same operation using eth_account, one yields the following signature;
0x40911813bd523b3dbc83f5eb06d024fb43d09609068842dba37c53527fabc33e
3ec391e743b820de01600842f7b23af1b19786e5778766f7e94798bfe500807a
1c
Notice how there are two intermediate hex strings within the signatures (f842a0 and a0). I am not quite sure where these are originating from.
Hello....me again ๐
Does this awesome library make signgniture for other chains like BSC,Polygon,Arbitrum?
These:
libethc/examples/legacy-transaction.c
Lines 62 to 63 in 60a518f
ok(eth_rlp_uint8(&rlp1, r))
and ok(eth_rlp_uint8(&rlp1, s))
hello bro ....please open another branch "dev" to make things easy for other contributers to suggest new feature or a change in the code...
Hello bro. I am trying to sign this contract on Uniswapv2 router 02
function swapExactETHForTokens(uint amountOutMin, address[] calldata path, address to, uint deadline)
external
payable
returns (uint[] memory amounts);
and i write thos code....
struct eth_abi abi;
char *fn = "swapExactETHForTokens(uint amountOutMin, address[] calldata path, address to, uint deadline)",
*addr = "0x7a250d5630B4cF539739dF2C5dAcb4c659F2488D", *hex;
char *weth="0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2";
char *usdt="0xdAC17F958D2ee523a2206206994597C13D831ec7";
char *myaddress="0xa9d0a7dC416f586491f2fb596731598F937617b5";
size_t hexlen;
ok(eth_abi_init(&abi, ETH_ABI_ENCODE));
ok(eth_abi_call(&abi, &fn, NULL));
ok(eth_abi)
ok(eth_abi_init(&abi, 0));
ok(eth_abi_array(&abi, ETH_ABI_ENCODE));
ok(eth_abi_address(&abi,&weth));
ok(eth_abi_address(&abi,&usdt));
ok(eth_abi_array_end(&abi));
/*i try to add string "account" but i don't know how*/
ok(eth_abi_call_end(&abi));
ok(eth_abi_to_hex(&abi, &hex, &hexlen));
ok(eth_abi_free(&abi));
printf("encoded abi: %s\n", hex);
free(hex);
But as u can see the comment found in the code, i have hard time to pass string to the ABI. and also where should i add the contract address?
If u can, can u show me how i sign this contract correctly and to send to the RPC-API eth_sendRawTransaction
?plsss
Possible fixes:
len
parameter of eth_abi_array
on encode. If it's set, just accept it as the actual length.brew install ethc
pacman -S ethc
apt-get install ethc
yum install ethc
How should I compile on Windows?
This warning pops up when configuring the project using cmake (in libkeccak/CMakeLists.txt
). This can be easily fixed by increasing the minimum required cmake version for that config file.
Is there a way to encode an array of tuples? Would like to do the following in ethc but didn't seem like it was supported
from eth_abi.abi import encode
print(encode(("(uint64,uint64)[]",),([(1,2),(3,4)],)).hex())
Hello brother. i'm trying to decode string data type ABI response using this code
char *data ="0x000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000045553444300000000000000000000000000000000000000000000000000000000";
// decoding
struct eth_abi abi1;
uint8_t *add;
eth_abi_from_hex(&abi1, data, -1);
eth_abi_bytes(&abi1, &add, NULL);
eth_abi_free(&abi1);
cout<<add<<endl;
and the out put is USDCPU
. the supposed out put is USDC
(u can check using this ABI decoder ).The function i called is
function name() external pure returns (string memory);
sometimes the decoder works fine and sometimes not. Here is when the decoder works fine
The data
0x0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000650415245544f0000000000000000000000000000000000000000000000000000
Decoded result PARETO
supposed result PARETO
Logs:
ok 426
*** stack smashing detected ***: terminated
Aborted (core dumped)
has to be related toeth_abi_mpint
Originally posted by DerXanRam September 22, 2023
I'm trying to swap on Binance Smart Chain(which this library also works for it) using 1inch dex. But it says sometimes
"message":"insufficient funds for gas * price + value"
and some times
"message":"INTERNAL_ERROR: insufficient funds"
even if i have fund in my account to do the swap and cover the gas. all my balance is BNB and i'm swaping BNB(0xeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee) to BUSD(0xe9e7cea3dedca5984780bafc599bd69add087d56).
this are the values used in making the raw tnx
nonce=0x1
gasPrice is 0xd09dc300
GasLimit is 0x42c23
value is 0x2386f26fc10000
ToAddress is 0x1111111254eeb25477b68fb85ed929f73a960582
The ABI data is
0x12aa3caf000000000000000000000000f8a1527325bb62d6d0320eb2312748d590f1ce27000000000000000000000000eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee000000000000000000000000e9e7cea3dedca5984780bafc599bd69add087d56000000000000000000000000f8a1527325bb62d6d0320eb2312748d590f1ce27000000000000000000000000b438d71c1e6e8e53637e1f1dec37c2e635e335fc000000000000000000000000000000000000000000000000002386f26fc100000000000000000000000000000000000000000000000000001cfbbfaad4cc354a0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000014000000000000000000000000000000000000000000000000000000000000001600000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000016800000000000000000000000000000000000000000000000000014a00001a4041bb4cdb9cbd36b01bd1cbaebf2de08d9173bc095cd0e30db05120830c9e0295730bbb220bd78346c6499ff37851fbbb4cdb9cbd36b01bd1cbaebf2de08d9173bc095c00a4a5dcbcdf000000000000000000000000bb4cdb9cbd36b01bd1cbaebf2de08d9173bc095c000000000000000000000000e9e7cea3dedca5984780bafc599bd69add087d560000000000000000000000002c93437fa01c0123ed21e8b862762c887c1195130000000000000000000000001111111254eeb25477b68fb85ed929f73a960582ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000008b1ccac8
and this is the raw tnx generated
f9036f0184d09dc30083042c23941111111254eeb25477b68fb85ed929f73a96058280b9030812aa3caf000000000000000000000000f8a1527325bb62d6d0320eb2312748d590f1ce27000000000000000000000000eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee000000000000000000000000e9e7cea3dedca5984780bafc599bd69add087d56000000000000000000000000f8a1527325bb62d6d0320eb2312748d590f1ce27000000000000000000000000b438d71c1e6e8e53637e1f1dec37c2e635e335fc000000000000000000000000000000000000000000000000002386f26fc100000000000000000000000000000000000000000000000000001cfbbfaad4cc354a0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000014000000000000000000000000000000000000000000000000000000000000001600000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000016800000000000000000000000000000000000000000000000000014a00001a4041bb4cdb9cbd36b01bd1cbaebf2de08d9173bc095cd0e30db05120830c9e0295730bbb220bd78346c6499ff37851fbbb4cdb9cbd36b01bd1cbaebf2de08d9173bc095c00a4a5dcbcdf000000000000000000000000bb4cdb9cbd36b01bd1cbaebf2de08d9173bc095c000000000000000000000000e9e7cea3dedca5984780bafc599bd69add087d560000000000000000000000002c93437fa01c0123ed21e8b862762c887c1195130000000000000000000000001111111254eeb25477b68fb85ed929f73a960582ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000008b1ccac88193a0e67028be55afd7e2d967d969b1ca6ad19cc87b9a4157701c12704675fa21d560a06767242acafe600388c1909d0b599417f85937c0c069b9c6dddbf5075d070010
any encoding error ?Please help ๐
It's good to have a function that determines how many bytes it takes to encode the integer instead of manually specifying it. Can be really useful when encoding/decoding non-deterministic recovery id v
in the signature.
uint64_t v = 12345;
eth_rlp_uint(&abi, &v); // 12345 occupies 2 bytes (0x3039)
I think it would be cool if we had cpp wrappers for our C functions. Let's say we want to encode some ABI elements:
#include <ethc/ethcxx.h> // maybe just ethc.hh?
int main(void) {
eth::ABIEncoder abi;
abi.encodeUint16(0xffac); // or abi.decodeUint16 on decode? and it returns the decoded element?
std::cout << abi << std::endl; // ABIEncoder supports streams?
return 0;
}
Hello bro.... To day i was testing the ABI encoder using this code
char *ABIFunction()
{
struct eth_abi abi;
char *fn = "allPairs(uint)", *hex;
uint64_t num = 2;
size_t hexlen;
uint64_t amount_out_min = 0, deadline = 346744838;
//////////////////
eth_abi_init(&abi, ETH_ABI_ENCODE);
eth_abi_call(&abi, &fn, NULL);
eth_abi_uint64(&abi,&num);
eth_abi_call_end(&abi);
ok(eth_abi_to_hex(&abi, &hex, &hexlen));
ok(eth_abi_free(&abi));
return hex;
}
The generated hex is
0xe9e0f23f0000000000000000000000000000000000000000000000000000000000000002
when i send this to eth_call
RPC, the generated RPC response is
{"error":{"code":-32000,"message":"execution reverted"},"id":0,"jsonrpc":"2.0"}
But when i use https://abi.hashex.org/ to generate the ABI, the ABI hex is
0x1e3dd18b0000000000000000000000000000000000000000000000000000000000000002
and when i send it to The RPC, the same way i sent the above ABI data, The RPC response is
{"id":0,"jsonrpc":"2.0","result":"0x00000000000000000000000012ede161c702d1494612d19f05992f43aa6a26fb"}
which is success. As u can see the ABI generated by the code and by the website, The difference is found only in the first 10 digits. Can u look at it please? Thanks ๐
int eth_abi_mpint(struct eth_abi *abi, mpz_t *mpz)
Hello bro. how u doing...... after converting my real private key to bytes and sign a real transaction there are two problems. The first one is, as u mentioned in the previous issue, u suggest me to use this website to make ABI. But when i compare the result of ABI generated by the code and by the website, they differ slightly with the same input...see below
By the website
0x7ff36ab500000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000080000000000000000000000000a9d0a7dc416f586491f2fb596731598f937617b50000000000000000000000000000000000000000000000000000000014aae8060000000000000000000000000000000000000000000000000000000000000002000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc2000000000000000000000000dac17f958d2ee523a2206206994597c13d831ec7
By the code
0xfda71c7f00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000080000000000000000000000000a9d0a7dc416f586491f2fb596731598f937617b50000000000000000000000000000000000000000000000000000000014aae8060000000000000000000000000000000000000000000000000000000000000002000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc2000000000000000000000000dac17f958d2ee523a2206206994597c13d831ec7
See the first 10 digits ... they differ at that point, the rest is the same.
After this i generated raw transaction using the code below,my address(no balance), the address's real private key and the ABI generated by the website. the code is
char *SignTransaction()
{
char *abi_result="0x7ff36ab500000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000080000000000000000000000000a9d0a7dc416f586491f2fb596731598f937617b50000000000000000000000000000000000000000000000000000000014aae8060000000000000000000000000000000000000000000000000000000000000002000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc2000000000000000000000000dac17f958d2ee523a2206206994597c13d831ec7";// = ABIFunction();
struct eth_rlp rlp0, rlp1;
struct eth_ecdsa_signature sign;
uint8_t privkey[] ={0x80, 0x3e, 0x53, 0x83, 0x51, 0x93, 0xdd, 0x6e,
0xad, 0x61, 0xa2, 0x5a, 0x74, 0x5f, 0xa6, 0x35,
0x86, 0xb4, 0xb2, 0xdd, 0x7b, 0x6a, 0xbe, 0x4a,
0x06, 0xfa, 0x7f, 0x33, 0xc1, 0x1a, 0xed, 0x81}; //real private key of the account 0xa9d0a7dC416f586491f2fb596731598F937617b5
//ok(eth_hex_to_bytes(&privkey,keys,64));
uint8_t nonce = 0x00, zero = 0x00, keccak[32], *rlp0bytes, *r, *s;
char *gasprice = "0x04a817c800", *gaslimit = "0x5208", *value = "0x00";
char *toaddr = "0x7a250d5630B4cF539739dF2C5dAcb4c659F2488D", *txn;
uint16_t chainid = 0x1, v;
size_t rlp0len, rlp1len, siglen = 32;
ok(eth_rlp_init(&rlp0, ETH_RLP_ENCODE));
ok(eth_rlp_array(&rlp0));
ok(eth_rlp_uint8(&rlp0, &nonce));
ok(eth_rlp_hex(&rlp0, &gasprice, NULL));
ok(eth_rlp_hex(&rlp0, &gaslimit, NULL));
ok(eth_rlp_address(&rlp0, &toaddr));
ok(eth_rlp_hex(&rlp0, &value, NULL));
ok(eth_rlp_hex(&rlp0, &abi_result, NULL));
ok(eth_rlp_uint16(&rlp0, &chainid));
ok(eth_rlp_uint8(&rlp0, &zero)); // 0x,
ok(eth_rlp_uint8(&rlp0, &zero)); // 0x,
ok(eth_rlp_array_end(&rlp0)); // ]
ok(eth_rlp_to_bytes(&rlp0bytes, &rlp0len, &rlp0));
ok(eth_rlp_free(&rlp0));
// compute the keccak hash of the encoded rlp elements
ok(eth_keccak256(keccak, rlp0bytes, rlp0len));
free(rlp0bytes);
// sign the transaction
ok(eth_ecdsa_sign(&sign, privkey, keccak));
// calculate v
v = sign.recid + chainid * 2 + 35;
r = sign.r;
s = sign.s;
ok(eth_rlp_init(&rlp1, ETH_RLP_ENCODE));
ok(eth_rlp_array(&rlp1));
ok(eth_rlp_uint8(&rlp1, &nonce));
ok(eth_rlp_hex(&rlp1, &gasprice, NULL));
ok(eth_rlp_hex(&rlp1, &gaslimit, NULL));
ok(eth_rlp_address(&rlp1, &toaddr));
ok(eth_rlp_hex(&rlp1, &value, NULL));
ok(eth_rlp_hex(&rlp1, &abi_result, NULL)); // replaced
ok(eth_rlp_uint16(&rlp1, &v));
ok(eth_rlp_bytes(&rlp1, &r, &siglen));
ok(eth_rlp_bytes(&rlp1, &s, &siglen));
ok(eth_rlp_array_end(&rlp1));
// FIX3: this actually returns the output length
ok(eth_rlp_to_hex(&txn, &rlp1) > 0);
ok(eth_rlp_free(&rlp1));
return txn;
}
and the RPC response is
{
"error": "rlp: non-canonical integer (leading zero bytes) for *big.Int, decoding into (*types.Transaction)(types.LegacyTx).V"
}
which seems formatting issue. i try to look on the internet about the problem and i found this forum answer. They say this happens because S
have leading zero byte. I try to work around in the libethc, But I couldn't fix it. Can u check it please?
Hello bro. I was working arround decoding data in the transaction to parameters(see this discussion) ... the decoding process works when parameters are not array. but when they are array eth_abi_array(&abi,&arrlen);
is not returning correct array size .. take a look the data, code and the output
data
0xd06ca61f00000000000000000000000000000000000000000000000000000000000027100000000000000000000000000000000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000000200000000000000000000000055d398326f99059ff775485246999027b319795500000000000000000000000055d398326f99059ff775485246999027b3197955
code
void abiDecoder(string data)
{
char *input = strdup(data.c_str());
char *fn="quote(uint256,address[])";
mpz_t num;
mpz_init(num);
uint64_t arrlen;
// decoding
struct eth_abi abi;
eth_abi_from_hex(&abi,input,data.length());
eth_abi_call(&abi, &fn, NULL);
eth_abi_mpint(&abi,num);
eth_abi_array(&abi,&arrlen);
char *add[arrlen];
for(uint64_t i=0;i<arrlen;i++)
eth_abi_address(&abi,&add[i]);
eth_abi_array_end(&abi);
eth_abi_call_end(&abi);
ok(eth_abi_free(&abi));
cout<<"arr len is "<<arrlen<<endl;
//char *final = (char *)bytes;
cout << "decoded " <<add[0] << endl;
}
output
arr len is 0
decoded ๏ฟฝ[UUU
and if i set the array size manually, decoded result misses offset and results incorrect form. This is the output when i set the array size to 2 manually
arr len is 2
decoded 0000000055d398326f99059ff775485246999027
The problem is not only in address
array, it also exists in other data types.
The data is encoded correctly and u can check it using this website and using this uniswapv2 abi contract
the function is
quote(uint256,address[])
and the value inside the data are
uint256=10000
address[]=[0x55d398326f99059ff775485246999027b3197955,0x55d398326f99059ff775485246999027b3197955]
when i try to compile example "ERC20 balanceOf call" from the documentation it throughs this error
/usr/bin/ld: /home/biruk/Documents/eth/main.c:69: undefined reference to `eth_rlp_free'
collect2: error: ld returned 1 exit status
Build finished with error(s).
* The terminal process terminated with exit code: -1.
I running ubuntu OS and all dependecies are installed correctly. I use Vscode as an IDE and the compiler(gcc) configuration "tasks.json" is :-
{
"tasks": [
{
"type": "cppbuild",
"label": "C/C++: gcc build active file",
"command": "/usr/bin/gcc",
"args": [
"-fdiagnostics-color=always",
"-g",
"${file}",
"-o",
"${fileDirname}/${fileBasenameNoExtension}"
],
"options": {
"cwd": "${fileDirname}"
},
"problemMatcher": [
"$gcc"
],
"group": {
"kind": "build",
"isDefault": true
},
"detail": "Task generated by Debugger."
},
{
"type": "cppbuild",
"label": "C/C++: gcc-11 build active file",
"command": "/usr/bin/gcc-11",
"args": [
"-fdiagnostics-color=always",
"-g",
"${file}",
"-o",
"${fileDirname}/${fileBasenameNoExtension}"
],
"options": {
"cwd": "${fileDirname}"
},
"problemMatcher": [
"$gcc"
],
"group": "build",
"detail": "Task generated by Debugger."
}
],
"version": "2.0.0"
}
Please help
we can create two separate functions to sign both recoverable and unrecoverable signatures
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.