CAPL convert an Byte array to ascii string - string

i have an byte array that i need to convert to ascii string before i save it as a system variable.
so i have a byte array like [63 6c 65 61 72]. i need to convert it to 'clear' before i store it in a system variable.
for (i = 0; i < elcount(gByteValue); i++)
{
snprintf(tmp, elcount(tmp), "%.2X ", gByteValue[i]); // byte to HEX convert
strncat(gStringValue, tmp, elcount(gStringValue)); // Concatenate HEX value to output string
}
write("String : %s", gStringValue);

Related

Vala - Bytes convert to string?

I have a GLib.Bytes object.
I want to print it and use it as a string like this:
Bytes bytes = new Bytes({65, 66, 67});
print(bytes); // <-- ERROR
How can I convert it to string?
Get raw byte array uint8[] with Bytes.get_data() and cast it as string.
Example:
Bytes bytes = new Bytes({65, 66, 67});
string str = (string)bytes.get_data();
print(str);
Output:
ABC

How to get the right values when I convert hex to ascii character

I'm trying to convert a hexa file to text, using javascript node js.
function hex_to_ascii(str1){
var hex = str1.toString();
var str = '';
for (var n = 0; n < hex.length; n += 2) {
str += String.fromCharCode(parseInt(hex.substr(n, 2), 16));
}
return str;
}
I have a problem concening the extended ASCII charaters, so for example when I try to convert 93 I've get “ instead of ô and when I convert FF I've get ÿ instead of (nbsp) space.
I want to get the same extended charaters as this table: https://www.rapidtables.com/code/text/ascii-table.html
This problem is slightly more complex than it seems at first, since you need to specify an encoding when converting from extended ascii to a string. For example Windows-1252, ISO-8859-1 etc. Since you wish to use the linked table, I'm assuming you wish to use CP437 encoding.
To convert a buffer to string you need a module that will do this for you, converting from a buffer (in a given encoding) to string is not trivial unless the buffer is in a natively supported node.js encoding, e.g. UTF-8, ASCII (7-bit only!), Latin1 etc.
I would suggest using the iconv-lite package, this will convert many types of encoding. Once this is installed the code should look as follows (this takes each character from 0x00 to 0xFF and prints the encoded character):
const iconv = require('iconv-lite');
function hex_to_ascii(hexData, encoding) {
const buffer = Buffer.from(hexData, "hex");
return iconv.decode(buffer, encoding);
}
const testInputs = [...Array(256).keys()];
const encoding = "CP437";
console.log("Decimal\tHex\tCharacter")
for(let input of testInputs) {
console.log([input, input.toString(16), hex_to_ascii(input.toString(16), encoding)].join("\t"));
}

How to convert to ascii using node.js

I am trying to convert length message to ascii.
My length message is like
var ll = "0170";
In node js , is there some kind of function which converts into ascii?
Please help?
Here's a simple function(ES6) which converts a string into ASCII characters using charCodeAt()
const toAscii = (string) => string.split('').map(char=>char.charCodeAt(0)).join(" ")
console.log(toAscii("Hello, World"))
Output:
-> 72 101 108 108 111 44 32 87 111 114 108 100
You could create a prototype function aswell. There are many solutions :)
you can't have an ascii code for a whole string.
An ascii code is an integer value for a character, not a string. Then for your string "0170" you will get 4 ascii codes
you can display these ascii codes like this
var str = "0170";
for (var i = 0, len = str.length; i < len; i++) {
console.log(str[i].charCodeAt());
}
Ouput : 48 49 55 48
use charCodeAt() function to covert asscii format.
var ll = "0170";
function ascii (a) { return a.charCodeAt(); }
console.log(ascii(ll[0]),ascii(ll[1]), ascii(ll[2]), ascii(ll[3]) )
result:
48 49 55 48

How to convert []int8 to string

What's the best way (fastest performance) to convert from []int8 to string?
For []byte we could do string(byteslice), but for []int8 it gives an error:
cannot convert ba (type []int8) to type string
I got the ba from SliceScan() method of *sqlx.Rows that produces []int8 instead of string
Is this solution the fastest?
func B2S(bs []int8) string {
ba := []byte{}
for _, b := range bs {
ba = append(ba, byte(b))
}
return string(ba)
}
EDIT my bad, it's uint8 instead of int8.. so I can do string(ba) directly.
Note beforehand: The asker first stated that input slice is []int8 so that is what the answer is for. Later he realized the input is []uint8 which can be directly converted to string because byte is an alias for uint8 (and []byte => string conversion is supported by the language spec).
You can't convert slices of different types, you have to do it manually.
Question is what type of slice should we convert to? We have 2 candidates: []byte and []rune. Strings are stored as UTF-8 encoded byte sequences internally ([]byte), and a string can also be converted to a slice of runes. The language supports converting both of these types ([]byte and []rune) to string.
A rune is a unicode codepoint. And if we try to convert an int8 to a rune in a one-to-one fashion, it will fail (meaning wrong output) if the input contains characters which are encoded to multiple bytes (using UTF-8) because in this case multiple int8 values should end up in one rune.
Let's start from the string "世界" whose bytes are:
fmt.Println([]byte("世界"))
// Output: [228 184 150 231 149 140]
And its runes:
fmt.Println([]rune("世界"))
// [19990 30028]
It's only 2 runes and 6 bytes. So obviously 1-to-1 int8->rune mapping won't work, we have to go with 1-1 int8->byte mapping.
byte is alias for uint8 having range 0..255, to convert it to []int8 (having range -128..127) we have to use -256+bytevalue if the byte value is > 127 so the "世界" string in []int8 looks like this:
[-28 -72 -106 -25 -107 -116]
The backward conversion what we want is: bytevalue = 256 + int8value if the int8 is negative but we can't do this as int8 (range -128..127) and neither as byte (range 0..255) so we also have to convert it to int first (and back to byte at the end). This could look something like this:
if v < 0 {
b[i] = byte(256 + int(v))
} else {
b[i] = byte(v)
}
But actually since signed integers are represented using 2's complement, we get the same result if we simply use a byte(v) conversion (which in case of negative numbers this is equivalent to 256 + v).
Note: Since we know the length of the slice, it is much faster to allocate a slice with this length and just set its elements using indexing [] and not calling the built-in append function.
So here is the final conversion:
func B2S(bs []int8) string {
b := make([]byte, len(bs))
for i, v := range bs {
b[i] = byte(v)
}
return string(b)
}
Try it on the Go Playground.
Not entirely sure it is the fastest, but I haven't found anything better.
Change ba := []byte{} for ba := make([]byte,0, len(bs) so at the end you have:
func B2S(bs []int8) string {
ba := make([]byte,0, len(bs))
for _, b := range bs {
ba = append(ba, byte(b))
}
return string(ba)
}
This way the append function will never try to insert more data that it can fit in the slice's underlying array and you will avoid unnecessary copying to a bigger array.
What is sure from "Convert between slices of different types" is that you have to build the right slice from your original int8[].
I ended up using rune (int32 alias) (playground), assuming that the uint8 were all simple ascii character. That is obviously an over-simplification and icza's answer has more on that.
Plus the SliceScan() method ended up returning uint8[] anyway.
package main
import (
"fmt"
)
func main() {
s := []int8{'a', 'b', 'c'}
b := make([]rune, len(s))
for i, v := range s {
b[i] = rune(v)
}
fmt.Println(string(b))
}
But I didn't benchmark it against using a []byte.
Use unsafe package.
func B2S(bs []int8) string {
return strings.TrimRight(string(*(*[]byte)unsafe.Pointer(&bs)), "\x00")
}
Send again ^^

C++ converting hex number to human readable string representation

I have a char[32] that consist of ASCII characters, some of which may be non printable characters, however, they are all in valid range of 0 to 255.
Let's say, it contains these numbers:
{ 9A 2E 5C 66 26 3D 5A 88 76 26 F1 09 B5 32 DE 10 91 3E 68 2F EA 7B C9 52 66 23 9D 77 16 BB C9 42 }
I'd like to print out or store in std::string as "9A2E5C66263D5A887626F109B532DE10913E682FEA7BC95266239D7716BBC942", however, if I print it out using printf or sprintf, it will yield the ASCII representative of each number, and instead it will print out "ö.\f&=Zàv&Ò µ2fië>h/Í{…Rf#ùwª…B", which is the correct ASCII character representation, since: ö = 9a, . = 2e, ...
How do I reliably get the string representation of the hex numbers? ie: I'd expect a char[64] which contains "9A2E5C66263D5A887626F109B532DE10913E682FEA7BC95266239D7716BBC942" instead.
Thanks!
void bytesToHex(char* dest, char* src, int size) {
for (unsigned int i = 0; i < size; i++) {
sprintf(&dest[i * 2], "%02x", src[i]);
}
}
You'd have to allocate your own memory here.
It would be used like this:
char myBuffer[32]
char result[65];
bytesToHex(result, myBuffer, 32);
result[64] = 0;
// print it
printf(result);
// or store it in an std::string
std::string str = string(result);
I tried:
char szStringRep[64];
for ( int i = 0; i < 32; i++ ) {
sprintf( &szStringRep[i*2], "%x", szHash[i] );
}
it works as intended, but if it encountered a < 0x10 number, it will null terminated as it is printing 0
You can encode your string to another system like Base64, which is widely used when using encryption algorithms.

Resources