Конкатенация строк добавляет нежелательные символы с типами - PullRequest
0 голосов
/ 20 марта 2011

Я добавляю «00000000» к строке, и она отлично работает в первый раз.Однако при повторном запуске вместо «000000» добавляются «символы барахла».Это пример кода, как я делаю это в реальной программе.

Файл one.py

# File One.py
from two import *

def One():
    while(1):
        key = Two()
        key = key + "00000000"
        print key

def main():
    One()

if __name__ == "__main__":
    main()

Файл two.py

from ctypes import *
import binascii

handle = None

def Two():
    global handle
    libc = CDLL('libthree.so', DEFAULT_MODE, handle) 
    if not handle: 
        handle = libc._handle

    buffer = create_string_buffer(16)
    libc.Three(buffer)
    return binascii.b2a_hex(buffer)

Файл три.c - генерирует libthree.so

#include "stdio.h"
#include "stdlib.h"

void Three(char * buffer)
{
    long value = 0x78563412;
    memcpy(buffer,&value,4);
    memcpy(buffer + 4,&value,4);
    memcpy(buffer+ 8,&value,4);
    memcpy(buffer+ 12,&value,4);
    return;
}

int main()
{
    return 0;
}

1 Ответ

1 голос
/ 21 марта 2011

create_string_buffer можно инициализировать строкой или длиной. Если инициализируется строкой s, он выделяет пространство для len(s)+1 символов, чтобы можно было добавить завершающий нуль. Но если инициализировать с помощью целочисленного значения, create_string_buffer предполагает, что, поскольку вы человек, вы должны знать, что вы делаете, и выделяет столько места. К сожалению, ваш код на C записывается в полные 16 символов пробела, поэтому нет места для нулевого терминатора. Когда это работает для вас, совершенно случайно, что байт после выделенного хранилища оказывается равным 0 (нулю), заканчивая строку. Позже эта память используется для чего-то другого, и тогда вы получаете мусор. Попробуйте вместо этого использовать create_string_buffer(16+1) и посмотрите, улучшится ли для вас ситуация.

В документах также предлагается использовать метод .string() возвращаемого объекта строкового буфера, так что вы явно применяете семантику с нулевым символом в конце - альтернатива - .raw(), которая будет читать последние нули до определенного размера буфера. По иронии судьбы, если вы укажете key = key.raw() + "000000", это может дать вам буфер размером 16 символов, который вы изначально указали, и обойти таким образом ненужные символы.

Итак, вот две вещи, которые вы можете попробовать:

В одном, сделайте:

key = key.raw() + "00000000"

Или в два, изменить на:

buffer = create_string_buffer(16+1)

Но, пожалуйста, не делайте оба.

...