C# byte array conversion to VB.NET - c#

As per my last question I'm borrowing some code from the Opus project to integrate into VB.NET software.
Consider
byte[] buff = _encoder.Encode(segment, segment.Length, out len);
which I've translated to:
Dim buff(wavEnc.Encode(segment, segment.Length, len)) As Byte
It is throwing a:
Value of type '1-dimensional array of Byte' cannot be converted to 'Integer' error...
How can I fix this problem?

Try this:
Dim buff = wavEnc.Encode(segment, segment.Length, len)
Of course you can do a direct translation of the c#:
Dim buff As Byte() = wavEnc.Encode(segment, segment.Length, len)
No need for a type at all - let the compiler figure it out.

_encoder.Encode() is the right-hand side of an assignment. The left-hand side is a byte array.
The way you are using it in your VB sample is as an array dimensioner: an Integer.

Related

How to get back the data after Marshal.Copy(byte,0,ptr,len)?

we have used the foll. code to marshal the byte array - ie:copy to unmanaged memory space;
Marshal.Copy(byte,0,ptr,len)?
How do I put the data back into a byte array in another program?
Pls advice if my approach is correct :-
string aString = "some text";
byte[] theBytes = System.Text.Encoding.Default.GetBytes(aString);
// Marshal the managed struct to a native block of memory.
int myByteSize = theBytes.Length;
IntPtr pmyByte = Marshal.AllocHGlobal(myByteSize ); //this is pointer
try
{
Marshal.Copy(theBytes, 0, pmyByte , myByteSize );
.............
Following this, I would like to retrieve the data with in this unmanaged memory into a string variable, how do I achieve that?
In VB6 I am doing it using (may be helpful for someone who wants to pass data from c#.net to vb6 app):-
Call CopyMemory(buf(1), ByVal cds.lpData, cds.cbData)
a$ = StrConv(buf, vbUnicode)
a$ = Left$(a$, InStr(1, a$, Chr$(0)) - 1)
Form1.Print a$
How do I pick up the marshaled data in C#.NET?
This code assumes, that you know the unmanaged data length (someArraySize) and character encoding:
// create new managed array
var array = new byte[someArraySize];
// copy data from unmanaged memory, pointed by ptr, into managed array
Marshal.Copy(ptr, array, 0, someArraySize);
// convert array to string; this assumes, that array contains string in UTF-8 encoding
var s = Encoding.UTF8.GetString(array);

Converting byte array to string with correct encoding

I have this bit of C# code that I have translated to VB using http://www.developerfusion.com/tools/convert/csharp-to-vb/
private string DecodeToken (string token, string key)
{
byte [] buffer = new byte[0];
string decoded = "";
int i;
if (Scramble (Convert.FromBase64String(token), key, ref buffer))
{
for (i=0;i<buffer.Length;i++)
{
decoded += Convert.ToString((char)buffer[i]);
}
}
return(decoded);
}
Which, after a little modification, gives this:
Private Function DecodeToken(token As String, key As String) As String
Dim buffer As Byte()
Dim decoded As String = ""
Dim index As Integer
If Scramble(Convert.FromBase64String(token), key, buffer) Then
For index = 0 To buffer.Length - 1
decoded += Convert.ToString(ChrW(buffer(index)))
Next
'decoded = UTF8Encoding.ASCII.GetString(pbyBuffer)
'decoded = UnicodeEncoding.ASCII.GetString(pbyBuffer)
'decoded = ASCIIEncoding.ASCII.GetString(pbyBuffer)
End If
Return decoded
End Function
Scramble just rearranges the array in a specific way and I've checked the VB and C# outputs against each other so it can be ignored. It's inputs and outputs are byte arrays so it shouldn't affect the encoding.
The problem lies in that the result of this function is fed into a hashing algorithm which is then compared against the hashing signature. The result of the VB version, when hashed, does not match to the signature.
You can see from the comments that I've attempted to use different encodings to get the byte buffer out as a string but none of these have worked.
The problem appears to lie in the transalation of decoded += Convert.ToString((char)buffer[i]); to decoded += Convert.ToString(ChrW(buffer(index))).
Does ChrW produce the same result as casting as a char and which encoding will correctly duplicate the reading of the byte array?
Edit: I always have Option Strict On but it's possible that the original C# doesn't so it may be affected by implicit conversion. What does the compiler do in that situation?
Quick answer
decoded += Convert.ToString((char)buffer[i]);
is equivalent to
decoded &= Convert.ToString(Chr(buffer[i]));
VB.Net stops you taking the hacky approach used in the c# code, a Char is Unicode so consists of two bytes.
This looks likes a better implementation of what you have.
Private Function DecodeToken(encodedToken As String, key As String) As String
Dim scrambled = Convert.FromBase64String(encodedToken)
Dim buffer As Byte()
Dim index As Integer
If Not Scramble(scrambled, key, buffer) Then
Return Nothing
End If
Dim descrambled = new StringBuilder(buffer.Length);
For index = 0 To buffer.Length - 1
descrambled.Append(Chr(buffer(index)))
Next
Return descrambled.ToString()
End Function
have you tried the most direct code translation:
decoded += Convert.ToString(CType(buffer[i], char))
When covnerting a byte array to a string you should really make sure you know the encoding first though. If this is set in whatever is providing the byte array then you should use that to decode the string.
For more details on the ChrW (and Chr) functions look at http://msdn.microsoft.com/en-us/library/613dxh46%28v=vs.80%29.aspx . In essence ChrW assumes that the passed int is a unicode codepoint which may not be a valid assumption (I believe from 0 to 127 this wouldn't matter but the upper half of the byte might be different). if this is the problem then it will likely be accented and other such "special" characters that are causing the problem.
Give the following a go:
decoded += Convert.ToChar(foo)
It will work (unlike my last attempt that made assumptions about implicit conversions being framework specific and not language specific) but I can't guarantee that it will be the same as the .NET.
Given you say in comments you expected to use Encoding.xxx.GetString then why don't you use that? Do you know what the encoding was in the original string to byte array? If so then just use that. It is the correct way to convert a byte array to a string anyway since doing it byte by byte will definitely break for any multi-byte characters (clearly).
A small improvement
Private Function DecodeToken(encodedToken As String, key As String) As String
Dim scrambled = Convert.FromBase64String(encodedToken)
Dim buffer As Byte()
Dim index As Integer
If Not Scramble(scrambled, key, buffer) Then
Return Nothing
End If
Dim descrambled = System.Text.Encoding.Unicode.GetString(buffer, 0, buffer.Length);
Return descrambled
End Function

C# Convert to Byte Array

How can i convert this VBNet code into C#? (ByteToImage is a User Defined Function use to convert Byte Array into Bitmap.
Dim Bytes() As Byte = CType(SQLreader("ImageList"), Byte())
picStudent.Image = jwImage.ByteToImage(Bytes)
I tried
byte[] Bytes = Convert.ToByte(SQLreader("ImageList")); // Error Here
picStudent.Image = jwImage.ByteToImage(Bytes);
but it generates an error saying: Cannot implicitly convert type 'byte' to 'byte[]'
What i am doing is basically converting an Image from database to byte array and displaying it on the picturebox.
byte[] Bytes = (byte[]) SQLreader("ImageList");
picStudent.Image = jwImage.ByteToImage(Bytes);
Try this
byte[] Bytes = (byte[])SQLreader("ImageList");
Hope this helps
The problem is you have an array of bytes (byte[] in C# and Byte() in VB.Net) but the Convert.ToByte call just returns a simple byte. To make this work you need to cast the return of SQLreader to byte[].
There is no perfect analogous construct for CType in C# but a simple cast here should do the trick
byte[] Bytes = (byte[])SQLreader("ImageList");
CType is the equivalent of a type cast, not an actual conversion.Besides, Convert.ToByte tries to convert its input to a single byte, not an array. The equivalent code is
byte[] bytes=(byte[])SQLreader("ImageList");

How can I convert sbyte[] to base64 string?

How can I convert sbyte[] to base64 string?
I cannot convert that sbyte[] to a byte[], to keep interoperability with java.
You absolutely can convert the sbyte[] to a byte[] - I can pretty much guarantee you that the Java code will really be treating the byte array as unsigned. (Or to put it another way: base64 is only defined in terms of unsigned bytes...)
Just convert to byte[] and call Convert.ToBase64String. Converting to byte[] is actually really easy - although C# itself doesn't provide a conversion between the two, the CLR is quite happy to perform a reference conversion, so you just need to fool the C# compiler:
sbyte[] x = { -1, 1 };
byte[] y = (byte[]) (object) x;
Console.WriteLine(Convert.ToBase64String(y));
If you want to have a genuine byte[] you can copy:
byte[] y = new byte[x.Length];
Buffer.BlockCopy(x, 0, y, 0, y.Length);
but personally I'd stick with the first form.
class Program
{
static void Main()
{
sbyte[] signedByteArray = { -2, -1, 0, 1, 2 };
byte[] unsignedByteArray = (byte[])(Array)signedByteArray;
Console.WriteLine(Convert.ToBase64String(unsignedByteArray));
}
}

Converting VB.NET code to C#

I have the follwing VB.NET code I am trying to convert to C#.
Dim decryptedBytes(CInt(encryptedStream.Length - 1)) As Byte
I tried this:
int tempData = Convert.ToInt32(encryptedStream.Length - 1);
Byte decryptedBytes;
decryptedBytes = decryptedBytes[tempData];
But got this error message:
Cannot apply indexing with [] to an expression of type byte.
Please note that the VB.NET code works.
Using the SharpDevelop code converter, the output for your VB code is:
byte[] decryptedBytes = new byte[Convert.ToInt32(encryptedStream.Length - 1) + 1];
Note that VB specifies for upper bound of the array where C# specifies the length, so the converter added the "+ 1".
I would simplify that to:
byte[] decryptedBytes = new byte[(int)encryptedStream.Length];
byte[] decryptedBytes = new byte[(Int32)encryptedStream.Length];
By the way if you have further problems try this:
http://www.developerfusion.com/tools/convert/vb-to-csharp/

Categories