Как преобразовать строку в байтовый массив? - PullRequest
0 голосов
/ 05 июля 2019

У меня есть следующий символ *:

char*Problem = "\x8B\x15\x00\x00\x00\x00\x8B\x7C\x24\x14\x85\xC9\x74\x16\x8B\x03\x89\x01\x8B\x2D\x00\x00\x00\x00\x8B\x15\x00\x00\x00\x00\x8B\x0D\x00\x00\x00\x00\x83\xC1\x04"

Я пытаюсь получить это:

unsigned char buf[] = {0x8B, 0x15, 0x00, 0x00, 0x00, 0x00, 0x8B, 0x7C, 0x24, 0x14, 0x85, 0xC9, 0x74, 0x16, 0x8B, 0x03, 0x89, 0x01, 0x8B, 0x2D, 0x00, 0x00, 0x00, 0x00, 0x8B, 0x15, 0x00, 0x00, 0x00, 0x00, 0x8B, 0x0D, 0x00, 0x00, 0x00, 0x00, 0x83, 0xC1, 0x04};

Но по времени выполнения.Я читаю символ * из текстового поля.

Я попробовал следующее:

UnicodeString Maskstr = Edit2->Text; //My char*Problem above
const char *chr = AnsiString(Maskstr).c_str();
char* MaskConverted = const_cast<char*>( chr );
unsigned char NewArray[40];
strcpy( (char*) NewArray, MaskConverted  );

Я думал, что мой неподписанный символ теперь будет NewArray, но это не так.Так как получить правильный результат? ..

Я сейчас немного застрял.Есть идеи?

Спасибо!:)

Ответы [ 2 ]

1 голос
/ 06 июля 2019

Ваш пример неправильно инициализирует переменную Problem (она усекает данные) после 2-го байта.

Но давайте просто предположим, что ваш TEdit фактически содержит полный текст, которым вы являетесьинтересует. Содержит ли TEdit фактические необработанные байты , которые были расширены как есть до 16-битных символов Юникода, или содержит шестнадцатеричное представление необработанногобайт?Это делает БОЛЬШУЮ разницу в том, как вы обрабатываете текст.

Если текст содержит необработанных байтов , то ваш код обработки неправильно хранит указатель char* на данные, которые принадлежат временномуAnsiString, который уничтожается до того, как вы используете указатель, таким образом демонстрируя неопределенное поведение .Не уничтожайте AnsiString до тех пор, пока вы не скопируете его:

AnsiString Maskstr = Edit2->Text;
unsigned char NewArray[40];
strncpy(reinterpret_cast<char*>(NewArray), const_cast<char*>(s.c_str()), 40);

В качестве альтернативы, просто вообще не конвертируйте в AnsiString, вместо этого вы можете просто обрезать символы Юникода:

UnicodeString Maskstr = Edit2->Text;
unsigned char NewArray[40] = {};
int maxlen = Maskstr.Length();
if (maxlen > 40) maxlen = 40;
for(int i = 0; i < maxlen; ++i) {
    NewArray = static_cast<unsigned char>(Maskstr[i+1]);
}

Однако, если текст на самом деле содержит шестнадцатеричное представление необработанных байтов, то вам нужно проанализировать текст для декодировать шестнадцатеричные последовательности в действительные байты, например:

#include <stdio.h>

UnicodeString Maskstr = Edit2->Text;
const WideChar *ptr = Maskstr.c_str();
unsigned char NewArray[40] = {};
int maxlen = Maskstr.Length();
if (maxlen > 40) maxlen = 40;
for(int i = 0; i < maxlen; ++i)
{
    unsigned int b, numChars;
    if (swscanf(ptr, L"\\x%2x%n", &b, &numChars) != 1) break;
    NewArray[i] = static_cast<unsigned char>(b);
    ptr += numChars;
}
0 голосов
/ 06 июля 2019

Компилятор скомпилирует шестнадцатеричные значения с вкладками, но я не смог найти функцию для ее перевода - хотя Реми использует scanf.Я изменил вкладку на 0x формат и использовал strtol.

// convert hex string to char/byte values
size_t TForm1::TranslateTabbedHex(const AnsiString str, std::vector<unsigned char> & result)
{
  AnsiString char_str(str);
  char * pEnd;

  size_t pos = char_str.AnsiPos("\\");
  for( ; pos; pos = char_str.AnsiPos("\\") )
  {
    if( pos != 1)
      char_str.Delete(1, pos-1);

    char_str[1] = '0';
    result.push_back( strtol(char_str.c_str(), &pEnd, 0) );
    char_str.Delete(1,1);
  }

  return result.size();
}
//---------------------------------------------------------------------------

void TForm1::TestTranslateTabbedHex(std::vector<unsigned char> & result)
{
  unsigned char test_value[] = "\x8B\x15\x00\x00\x00\x00\x8B\x7C\x24\x14"
                               "\x85\xC9\x74\x16\x8B\x03\x89\x01\x8B\x2D"
                               "\x00\x00\x00\x00\x8B\x15\x00\x00\x00\x00"
                               "\x8B\x0D\x00\x00\x00\x00\x83\xC1\x04";

  //"\x8B\x15\x00\x00\x00\x00\x8B\x7C\x24\x14\x85\xC9\x74\x16\x8B\x03\x89\x01\x8B\x2D\x00\x00\x00\x00\x8B\x15\x00\x00\x00\x00\x8B\x0D\x00\x00\x00\x00\x83\xC1\x04"

  Memo1->Clear();

  size_t test_size =  sizeof test_value - 1;
  AnsiString length( test_size );
  Memo1->Lines->Add( AnsiString("size test_value=") + length );
  Memo1->Lines->Add( AnsiString("size result=") + result.size() );

  AnsiString text(Edit1->Text);
  if(Edit1->Text.Length() > 0)
    Memo1->Lines->Add( AnsiString("first char value in EditBox = ") + text[1]);
  else
    Memo1->Lines->Add("No text in EditBox");

  Memo1->Lines->Add(" ");

  if(result.size() == 0)
  { Memo1->Lines->Add("result = 0 length");
  }
  else
  { size_t test_size = std::min( result.size(), test_size );  // #include <algorithm>
    Memo1->Lines->Add("test  - result - same");
    for(size_t i=0; i<test_size; i++)
    { AnsiString line(test_value[i]);
      line += AnsiString("  -  ") + result[i];
      line += AnsiString("  -  ") + AnsiString((result[i] == test_value[i]) ? "Yes" : "No");
      Memo1->Lines->Add( line );
    }
  }
}
//---------------------------------------------------------------------------

void __fastcall TForm1::Button1Click(TObject *Sender)
{
  std::vector<unsigned char> result;
  TranslateTabbedHex(Edit1->Text, result);
  TestTranslateTabbedHex( result );
}
//---------------------------------------------------------------------------
...