реклама на сайте
подробности

 
 
> Самомодифицирующийся код в экосистеме Cortex-M., есть ли право на жизнь?
jcxz
сообщение Jun 28 2018, 22:54
Сообщение #1


Гуру
******

Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713



Есть мысль использовать самомодифицирующийся код для оптимизации решения одной задачи.
Именно самомодифицирующийся - программа строит часть самой себя по некоему алгоритму, а не просто копирует куски кода из одной области памяти в другую.
И вот я что-то не смог вспомнить чтобы здесь на форуме вообще когда-то поднималась эта тема.
Кто-то вообще использует такой код на ARM-ах в своих проектах? Просто интересно... rolleyes.gif

PS: И пожалуйста - без религиозной нетерпимости.
Go to the top of the page
 
+Quote Post
 
Start new topic
Ответов
AlexandrY
сообщение Jun 29 2018, 05:47
Сообщение #2


Ally
******

Группа: Модераторы
Сообщений: 6 232
Регистрация: 19-01-05
Пользователь №: 2 050



Цитата(jcxz @ Jun 29 2018, 01:54) *
PS: И пожалуйста - без религиозной нетерпимости.

Обещать не могу. biggrin.gif

А загрузчики считаются самомодифицирующимся кодом?
Или самомодифицирующийся - это код который вот именно сам себя модифицирует, т.е. инструкция STR вот прямо по своему адресу что-то и пишет и сама себя таким образом затирает.
Go to the top of the page
 
+Quote Post
jcxz
сообщение Jun 29 2018, 06:56
Сообщение #3


Гуру
******

Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713



Цитата(AlexandrY @ Jun 29 2018, 08:47) *
Или самомодифицирующийся - это код который вот именно сам себя модифицирует, т.е. инструкция STR вот прямо по своему адресу что-то и пишет и сама себя таким образом затирает.

Я уже выше написал: будет функция, которая по некоторым условиям пишет другую функцию. По командам. В маш.кодах. Команды записываемые в тело создаваемой функции (и их последовательность) зависят от аргументов первой функции.

PS: Вот уже сколько откликов получил, а на собственно единственный вопрос, поставленный в первом сообщении, так никто и не ответил. И видимо забыли все в чём был вопрос..... sad.gif
Вопрос был собственно в том: использовал кто-нить из здесь присутствующих самомодифицирующийся код (именно такой код, который или сам своё тело правит или строит другой код (а не просто копирует из одного места в другое))? Именно на платформе ARM в embedded?
И, если использовали, то для какой задачи?
Go to the top of the page
 
+Quote Post
AlexandrY
сообщение Jun 29 2018, 07:00
Сообщение #4


Ally
******

Группа: Модераторы
Сообщений: 6 232
Регистрация: 19-01-05
Пользователь №: 2 050



Цитата(jcxz @ Jun 29 2018, 09:56) *
Я уже выше написал: будет функция, которая по некоторым условиям пишет другую функцию. По командам. В маш.кодах. Команды записываемые в тело создаваемой функции (и их последовательность) зависят от аргументов первой функции.

Тогда я не согласен с названием "самомодифицирующийся", у меня загрузчики тоже загружают разные не то что функции, а целые программы(и да в машинных кодах, разумеется) в зависимости от аргументов.
Go to the top of the page
 
+Quote Post
Николай Семёнови...
сообщение Jun 29 2018, 16:00
Сообщение #5


Местный
***

Группа: Участник
Сообщений: 297
Регистрация: 20-05-17
Пользователь №: 97 202



Цитата(AlexandrY @ Jun 29 2018, 10:00) *
Тогда я не согласен с названием "самомодифицирующийся", у меня загрузчики тоже загружают разные не то что функции, а целые программы(и да в машинных кодах, разумеется) в зависимости от аргументов.

Попытаюсь объяснить (как я это понял), что подразумевать под "самомодифицирующимся кодом" топикстартер.

Не.

Не буду. Боюсь всё равно не поймёте
А разжигать холивар не хочу

Впрочем, скажу кое-что.
Ваш загрузчик просто подгружает целые законченные куски кода, а у топикстартера программа меняет отдельные команды своего собственного кода
Go to the top of the page
 
+Quote Post
jcxz
сообщение Jun 29 2018, 17:11
Сообщение #6


Гуру
******

Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713



Цитата(Николай Семёнович @ Jun 29 2018, 19:00) *
Ваш загрузчик просто подгружает целые законченные куски кода, а у топикстартера программа меняет отдельные команды своего собственного кода

Вот именно. Даже полностью строит процедуру. Вот такой примерно должен быть результат (код) работы генератора:
CODE
;Назначение регистров в динамически генерируемой функции.
dstReg EQU c_R0 ;указатель на целевой буфер для записи (вх.аргумент)
tblReg EQU c_R1 ;указатель на таблицу адресов переменных (вх.аргумент)
tmpReg0 EQU c_R2 ;рабочий регистр 0
tmpReg1 EQU c_R3 ;рабочий регистр 1
;сама функция
;f0 LDR tmpReg0, [tblReg, #bit1*4]; где bit1 - номер первого единичного бита в мл.слове бит-карты
;f0 LDR tmpReg1, [tblReg, #bit2*4]; где bit2 - номер второго единичного бита в мл.слове бит-карты
;f1 LDR/LDRH tmpReg0, [tmpReg0]
;f2 STR/STRH tmpReg0, [dstReg], #step; где step==4 для STR и step==2 для STRH
;f0 LDR tmpReg0, [tblReg, #bit3*4]; где bit3 - номер 3-го единичного бита в мл.слове бит-карты
;f1 LDR/LDRH tmpReg1, [tmpReg1]
;f2 STR/STRH tmpReg1, [dstReg], #step; где step==4 для STR и step==2 для STRH
;f0 LDR tmpReg1, [tblReg, #bit4*4]; где bit4 - номер 4-го единичного бита в мл.слове бит-карты
;f1 LDR/LDRH tmpReg0, [tmpReg0]
;f2 STR/STRH tmpReg0, [dstReg], #step; где step==4 для STR и step==2 для STRH
; ...
;f3 ADDS tblReg, tblReg, #32*4; вставляется при переходе к ст.слову бит-карты если в нём есть единицы
;f0 LDR tmpReg0, [tblReg, #bit1*4]; где bit1 - номер 1-го единичного бита в ст.слове бит-карты
;f1 LDR/LDRH tmpReg1, [tmpReg1]
;f2 STR/STRH tmpReg1, [dstReg], #step; где step==4 для STR и step==2 для STRH
;f0 LDR tmpReg1, [tblReg, #bit2*4]; где bit2 - номер 2-го единичного бита в ст.слове бит-карты
;f1 LDR/LDRH tmpReg0, [tmpReg0]
;f2 STR/STRH tmpReg0, [dstReg], #step; где step==4 для STR и step==2 для STRH
; ...
;f1 LDR/LDRH tmpReg1, [tmpReg1]
;f2 STR/STRH tmpReg1, [dstReg], #step; где step==4 для STR и step==2 для STRH
;f4 BX LR

LDR или LDRH использовать - определяется весом бита, заданным в таблице. Генератор формирует код глядя в эту таблицу.

Цитата(Arlleex @ Jun 29 2018, 19:18) *
Как видно, в любом случае нет больше в цикле инструкций проверки условий в if(...)-ах (а они же ведь по сути Bxx в ассемблерном представлении) (да и куда лучше вовсе не проверять заранее ложные условия по списку), а выполняются только нужные инструкции сразу, как будто условных конструкций и нет. А п. 1 и 2, конечно, требуют тактов, только для моего случая п. 1. требуется выполнить только 1 раз для всех итераций цикла, на этапе составления списка инструкций СМК.
Надеюсь, моя мысль будет так понятнее.

Блин, коллега, позвольте пожать Вашу руку! Вы - похоже почти единственный человек на этом форуме сходу понявший все нюансы!!! rolleyes.gif

Цитата(Arlleex @ Jun 29 2018, 19:56) *
Я просто телепат cool.gif

Как будто заглянули в мои исходники! cool.gif
Go to the top of the page
 
+Quote Post
Arlleex
сообщение Jun 29 2018, 17:18
Сообщение #7


Местный
***

Группа: Участник
Сообщений: 492
Регистрация: 12-11-11
Пользователь №: 68 264



Цитата(jcxz @ Jun 29 2018, 20:11) *
Блин, коллега, позвольте пожать Вашу руку! Вы - похоже почти единственный человек на этом форуме сходу понявший все нюансы!!! rolleyes.gif

О результатах сообщите, пожалуйста, удалось/не удалось внедрить, буду держать на всякий случай идею такую. Я довольно плотно поработал с битовой графикой на LCD/TFT дисплеях и организовывал меню разной степени вложенности для пользователей устройств с тачскрином/кнопками и экраном. Там таких ситуаций, где флажки надо опрашивать и определять отрисовки, да на каждом шагу по 50 biggrin.gif
Go to the top of the page
 
+Quote Post
jcxz
сообщение Jun 29 2018, 17:23
Сообщение #8


Гуру
******

Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713



Цитата(Arlleex @ Jun 29 2018, 20:18) *
О результатах сообщите, пожалуйста, удалось/не удалось внедрить, буду держать на всякий случай идею такую. Я довольно плотно поработал с битовой графикой на LCD/TFT дисплеях и организовывал меню разной степени вложенности для пользователей устройств с тачскрином/кнопками и экраном. Там таких ситуаций, где флажки надо опрашивать и определять отрисовки, да на каждом шагу по 50 biggrin.gif

Ок. Генератор написал, но отлаживать буду завтра - поздно уже. Как заработает - напишу.
У меня этот код предназначен для записи текущих значений переменных в поток. Карта выбранных для записи переменных приходит по интерфейсу связи и может меняться в процессе работы иногда, не прерывая процесса. Всего в программе много десятков таких переменных, которые хотелось бы писать, но писать все сразу - не хватит пропускной способности канала.
Переменные пока только 16- и 32-битные (целочисленные и float). Каждая битовая позиция в карте закреплена жёстко за какой-то переменной. И есть таблица указателей на эти переменные.
И это только - сервисная задача. Её выполнение не должно мешать выполнению основных рабочих задач МК, которых достаточно много и тяжёлых. Но в процессе работы нужно следить за всеми этими переменными.
Вот примерно так.
Go to the top of the page
 
+Quote Post
adnega
сообщение Jun 29 2018, 21:21
Сообщение #9


Гуру
******

Группа: Свой
Сообщений: 2 724
Регистрация: 14-05-07
Из: Ярославль, Россия
Пользователь №: 27 702



Цитата(jcxz @ Jun 29 2018, 20:23) *
Как заработает - напишу.

Проверил в железе - работает (Cortex-M0).

CODE
#include "stdafx.h"
#include "conio.h"
#include "windows.h"

#define IS_ALIGN (1)
#define VAR_NUM (32)

//-----------------------------------------------------------------------------
// enum eVAR_TYPE
//-----------------------------------------------------------------------------
enum eVAR_TYPE
{
VAR_NONE = 0,
VAR_DWORD,
VAR_WORD,
VAR_BYTE,
};

//-----------------------------------------------------------------------------
// typedef struct sVAR
//-----------------------------------------------------------------------------
typedef struct sVAR
{
union
{
DWORD data_dw;
WORD data_w;
BYTE data_b;
};
enum eVAR_TYPE type;
} sVAR;

volatile sVAR var[VAR_NUM] =
{
{0x12345678, VAR_DWORD},
{0xABCD, VAR_WORD},
{0x11223344, VAR_DWORD},
{0x55, VAR_BYTE},
{0x00, VAR_BYTE},
{0x66, VAR_BYTE},
{0x77, VAR_BYTE},
{0x88, VAR_BYTE},
{0x99, VAR_BYTE},
{0xAA, VAR_BYTE},
{0xBB, VAR_BYTE},
{0xCC, VAR_BYTE},
{0xDD, VAR_BYTE},
{0xEE, VAR_BYTE},
{0xFF, VAR_BYTE},
{0x98765432, VAR_DWORD},
};

BYTE exec_ram[1024];

//-----------------------------------------------------------------------------
// void set_new_mask(const DWORD mask)
//-----------------------------------------------------------------------------
void set_new_mask(const DWORD mask)
{
int offset;
int last_var = 0;
int s_pos = 0;
int exec_ram_pos = 0;

printf("// r0 = *s, r1 = var\n");

// PUSH {r2, lr}
exec_ram[exec_ram_pos++] = 0x04;
exec_ram[exec_ram_pos++] = 0xB5;

printf("B5 04 - push {r2, pc}\n");

for(int i = 0; i < VAR_NUM; i++)
{
if(mask & (1 << i))
{
switch(var[i].type)
{
case VAR_DWORD:
printf("// DWORD[%d]\n", i);

offset = (i - last_var) * 8;
last_var = i;

while(offset > 128)
{
offset -= 128;
// ADD r1, #128
exec_ram[exec_ram_pos++] = 128;
exec_ram[exec_ram_pos++] = 0x31;

printf("31 80 - add r1, #128\n");
}

if(offset)
{
// ADD r1, #offset
exec_ram[exec_ram_pos++] = offset;
exec_ram[exec_ram_pos++] = 0x31;

printf("31 %02X - add r1, #%d\n", offset, offset);
}

if(IS_ALIGN && (s_pos & 1))
{
// byte align

// LDRB r2, [r1, #0]
exec_ram[exec_ram_pos++] = 0x0A;
exec_ram[exec_ram_pos++] = 0x78;

printf("78 0A - ldrb r2, [r1, #0]\n");

// STRB r2, [r0, #0]
exec_ram[exec_ram_pos++] = 0x02;
exec_ram[exec_ram_pos++] = 0x70;

printf("70 02 - strb r2, [r0, #0]\n");

// LDRB r2, [r1, #1]
exec_ram[exec_ram_pos++] = 0x4A;
exec_ram[exec_ram_pos++] = 0x78;

printf("78 4A - ldrb r2, [r1, #1]\n");

// STRB r2, [r0, #1]
exec_ram[exec_ram_pos++] = 0x42;
exec_ram[exec_ram_pos++] = 0x70;

printf("70 42 - strb r2, [r0, #1]\n");

// LDRB r2, [r1, #2]
exec_ram[exec_ram_pos++] = 0x8A;
exec_ram[exec_ram_pos++] = 0x78;

printf("78 8A - ldrb r2, [r1, #2]\n");

// STRB r2, [r0, #2]
exec_ram[exec_ram_pos++] = 0x82;
exec_ram[exec_ram_pos++] = 0x70;

printf("70 82 - strb r2, [r0, #2]\n");

// LDRB r2, [r1, #3]
exec_ram[exec_ram_pos++] = 0xCA;
exec_ram[exec_ram_pos++] = 0x78;

printf("78 CA - ldrb r2, [r1, #3]\n");

// STRB r2, [r0, #3]
exec_ram[exec_ram_pos++] = 0xC2;
exec_ram[exec_ram_pos++] = 0x70;

printf("70 C2 - strb r2, [r0, #3]\n");
}
else if(IS_ALIGN && (s_pos & 2))
{
// word align

// LDRH r2, [r1, #0]
exec_ram[exec_ram_pos++] = 0x0A;
exec_ram[exec_ram_pos++] = 0x88;

printf("88 0A - ldrh r2, [r1, #0]\n");

// STRH r2, [r0, #0]
exec_ram[exec_ram_pos++] = 0x02;
exec_ram[exec_ram_pos++] = 0x80;

printf("80 02 - strh r2, [r0, #0]\n");

// LDRH r2, [r1, #2]
exec_ram[exec_ram_pos++] = 0x4A;
exec_ram[exec_ram_pos++] = 0x88;

printf("88 4A - ldrh r2, [r1, #2]\n");

// STRH r2, [r0, #2]
exec_ram[exec_ram_pos++] = 0x42;
exec_ram[exec_ram_pos++] = 0x80;

printf("80 42 - strh r2, [r0, #2]\n");
}
else
{
// dword align

// LDR r2, [r1, #0]
exec_ram[exec_ram_pos++] = 0x0A;
exec_ram[exec_ram_pos++] = 0x68;

printf("68 0A - ldr r2, [r1, #0]\n");

// STR r2, [r0, #0]
exec_ram[exec_ram_pos++] = 0x02;
exec_ram[exec_ram_pos++] = 0x60;

printf("60 02 - str r2, [r0, #0]\n");
}

// ADDS r0, #4
exec_ram[exec_ram_pos++] = 0x04;
exec_ram[exec_ram_pos++] = 0x30;

printf("30 04 - adds r0, #4\n");

s_pos += 4;
break;

case VAR_WORD:
printf("// WORD[%d]\n", i);

offset = (i - last_var) * 8;
last_var = i;

while(offset > 128)
{
offset -= 128;
// ADD r1, #128
exec_ram[exec_ram_pos++] = 128;
exec_ram[exec_ram_pos++] = 0x31;

printf("31 80 - add r1, #128\n");
}

if(offset)
{
// ADD r1, #offset
exec_ram[exec_ram_pos++] = offset;
exec_ram[exec_ram_pos++] = 0x31;

printf("31 %02X - add r1, #%d\n", offset, offset);
}

if(IS_ALIGN && (s_pos & 1))
{
// byte align

// LDRB r2, [r1, #0]
exec_ram[exec_ram_pos++] = 0x0A;
exec_ram[exec_ram_pos++] = 0x78;

printf("78 0A - ldrb r2, [r1, #0]\n");

// STRB r2, [r0, #0]
exec_ram[exec_ram_pos++] = 0x02;
exec_ram[exec_ram_pos++] = 0x70;

printf("70 02 - strb r2, [r0, #0]\n");

// LDRB r2, [r1, #1]
exec_ram[exec_ram_pos++] = 0x4A;
exec_ram[exec_ram_pos++] = 0x78;

printf("78 4A - ldrb r2, [r1, #1]\n");

// STRB r2, [r0, #1]
exec_ram[exec_ram_pos++] = 0x42;
exec_ram[exec_ram_pos++] = 0x70;

printf("70 42 - strb r2, [r0, #1]\n");
}
else
{
// word align

// LDRH r2, [r1, #0]
exec_ram[exec_ram_pos++] = 0x0A;
exec_ram[exec_ram_pos++] = 0x88;

printf("88 0A - ldrh r2, [r1, #0]\n");

// STRH r2, [r0, #0]
exec_ram[exec_ram_pos++] = 0x02;
exec_ram[exec_ram_pos++] = 0x80;

printf("80 02 - strh r2, [r0, #0]\n");
}

// ADDS r0, #2
exec_ram[exec_ram_pos++] = 0x02;
exec_ram[exec_ram_pos++] = 0x30;

printf("30 02 - adds r0, #2\n");

s_pos += 2;
break;

case VAR_BYTE:
printf("// BYTE[%d]\n", i);

offset = (i - last_var) * 8;
last_var = i;

while(offset > 128)
{
offset -= 128;
// ADD r1, #128
exec_ram[exec_ram_pos++] = 128;
exec_ram[exec_ram_pos++] = 0x31;

printf("31 80 - add r1, #128\n\r");
}

if(offset)
{
// ADD r1, #offset
exec_ram[exec_ram_pos++] = offset;
exec_ram[exec_ram_pos++] = 0x31;

printf("31 %02X - add r1, #%d\n", offset, offset);
}

// LDRB r2, [r1, #0]
exec_ram[exec_ram_pos++] = 0x0A;
exec_ram[exec_ram_pos++] = 0x78;

printf("78 0A - ldrb r2, [r1, #0]\n");

// STRB r2, [r0, #0]
exec_ram[exec_ram_pos++] = 0x02;
exec_ram[exec_ram_pos++] = 0x70;

printf("70 02 - strb r2, [r0, #0]\n");

// ADDS r0, #1
exec_ram[exec_ram_pos++] = 0x01;
exec_ram[exec_ram_pos++] = 0x30;

printf("30 01 - adds r0, #1\n");

s_pos += 1;
break;
}
}
}
printf("// EXIT\n");

// POP {r2, pc}
exec_ram[exec_ram_pos++] = 0x04;
exec_ram[exec_ram_pos++] = 0xBD;

printf("BD 04 - pop {r2, pc}\n");

#if 0
printf("SMC:\n");
for(int i = 0; i < exec_ram_pos / 2; i++)
printf("%02X %02X\n", exec_ram[i * 2 + 1], exec_ram[i * 2 + 0]);
#endif
}

int _tmain(int argc, _TCHAR* argv[])
{
set_new_mask(0xc7);
_getch();
return 0;
}




СМК:
CODE
// r0 = *s, r1 = var
B5 04 - push {r2, pc}
// DWORD[0]
68 0A - ldr r2, [r1, #0]
60 02 - str r2, [r0, #0]
30 04 - adds r0, #4
// WORD[1]
31 08 - add r1, #8
88 0A - ldrh r2, [r1, #0]
80 02 - strh r2, [r0, #0]
30 02 - adds r0, #2
// DWORD[2]
31 08 - add r1, #8
88 0A - ldrh r2, [r1, #0]
80 02 - strh r2, [r0, #0]
88 4A - ldrh r2, [r1, #2]
80 42 - strh r2, [r0, #2]
30 04 - adds r0, #4
// BYTE[6]
31 20 - add r1, #32
78 0A - ldrb r2, [r1, #0]
70 02 - strb r2, [r0, #0]
30 01 - adds r0, #1
// BYTE[7]
31 08 - add r1, #8
78 0A - ldrb r2, [r1, #0]
70 02 - strb r2, [r0, #0]
30 01 - adds r0, #1
// EXIT
BD 04 - pop {r2, pc}


Результат на Cortex-M0
Цитата
RESULT[20000F44]: 78 56 34 12 CD AB 44 33 22 11 77 88
Go to the top of the page
 
+Quote Post
jcxz
сообщение Jun 30 2018, 00:22
Сообщение #10


Гуру
******

Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713



Цитата(adnega @ Jun 30 2018, 00:21) *
Проверил в железе - работает (Cortex-M0).

мммм... неправильно laughing.gif
См. моё сообщение #39 - какой должен быть результат работы.
К тому же: a) const в аргументе set_new_mask() - лишнее; б) R2,LR в вашей функции - не нужно сохранять, см. соглашения вызова компилятора; в) даже по Вашему алгоритму копирования - очень неоптимально, количество команд в 2 раза больше, чем можно было бы (для Cortex-M4).
Go to the top of the page
 
+Quote Post
adnega
сообщение Jun 30 2018, 06:41
Сообщение #11


Гуру
******

Группа: Свой
Сообщений: 2 724
Регистрация: 14-05-07
Из: Ярославль, Россия
Пользователь №: 27 702



Цитата(jcxz @ Jun 30 2018, 03:22) *
мммм... неправильно

А что именно неправильно?
Есть таблица переменных состоящая из значений и типов.
Есть маска, где каждый бит связан с соответствующим элементом таблицы.
Есть функция-генератор, создающая в рантайме код, при выполнении которого
в выходной поток копируются данные из таблицы с учетом длины и заданной маски.
Для заданного var, RESULT (отработал СМК) такой ожидаете?
Если нет, то где ошибка?

Цитата(jcxz @ Jun 30 2018, 03:22) *
a) const в аргументе set_new_mask() - лишнее;

Ну, функция set_new_mask не должна менять mask, поэтому и const. Или я вас не понял.

Цитата(jcxz @ Jun 30 2018, 03:22) *
б) R2,LR в вашей функции - не нужно сохранять, см. соглашения вызова компилятора;

Вы же супер-скорость хотели. Выкидывайте push и pop - и вот вам готовый участок кода, дающий результат,
но не забудьте проинициализировать r0 и r1.
Если нужна именно как функция, то достаточно одного "bx lr" в конце.

Цитата(jcxz @ Jun 30 2018, 03:22) *
в) даже по Вашему алгоритму копирования - очень неоптимально, количество команд в 2 раза больше, чем можно было бы (для Cortex-M4).

Какие именно команды лишние? Можно IS_ALIGN обнулить, тогда генератор будет работать с невыровненными данными.
Попробую сегодня избавиться от лишних adds.
Go to the top of the page
 
+Quote Post
jcxz
сообщение Jun 30 2018, 07:21
Сообщение #12


Гуру
******

Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713



Цитата(adnega @ Jun 30 2018, 09:41) *
А что именно неправильно?
Есть таблица переменных состоящая из значений и типов.

Вы же ассемблер понимаете? Тогда посмотрите на требуемый результат (код) в сообщении #39 и поймёте в чём разница.
Нет таблицы переменных, есть таблица указателей на переменные. Так как эти переменные разбросаны по всей программе и объединить их в одну область памяти (структуру) нельзя. Они находятся в разных обособленных службах программы, и там и должны оставаться. А адресация их идёт через таблицу указателей. Я писал об этом. И в примере результата это чётко видно.
Если си-исходник будет понятней, то:
CODE
enum {N = <максимум 64>};
enum {TYP_s16, TYP_u16, TYP_s32, TYP_u32, TYP_float, TYP_n};
struct {
u8 main:3;
u8 misc:5;
} const isTyp[N] = {{TYP_s32, ...}, {TYP_u16, ...}, ...};
u8 isTypSize[TYP_n] = {2, 2, 4, 4, 4};
char *psrc;
char *pdst;
if (map & 1 << 0) {
psrc = varPtrs[0];
if (isTypSize[isTyp[0].main]) == 4) {
*(u32 *)pdst = *(u32 *)psrc;
pdst += 4;
} else {
*(u16 *)pdst = *(u16 *)psrc;
pdst += 2;
}
}
if (map & 1 << 1) {
psrc = varPtrs[1];
if (isTypSize[isTyp[1].main]) == 4) {
*(u32 *)pdst = *(u32 *)psrc;
pdst += 4;
} else {
*(u16 *)pdst = *(u16 *)psrc;
pdst += 2;
}
}
//и так далее... так сейчас в си-исходнике сделано. Цель СМК - построить оптимальный код выкинув кучу ненужных операций из этого алгоритма по текущей карте map, до следующего её изменения.


Цитата(adnega @ Jun 30 2018, 09:41) *
Какие именно команды лишние? Можно IS_ALIGN обнулить, тогда генератор будет работать с невыровненными данными.
Попробую сегодня избавиться от лишних adds.

У меня Cortex-M4. Он поддерживает команды с пост- и пре- модификациями адреса. Например: LDR R0, [R1], #4 тогда ваш код сократится в 2 раза.
Да я уже вчера всё сделал. И даже больше. Мой генератор ещё и перемежение команд поддерживает для исключения штрафов между командами LDR. rolleyes.gif
И я его на асме написал. Хотя это просто из спортивного интереса. cool.gif
Go to the top of the page
 
+Quote Post
adnega
сообщение Jun 30 2018, 08:59
Сообщение #13


Гуру
******

Группа: Свой
Сообщений: 2 724
Регистрация: 14-05-07
Из: Ярославль, Россия
Пользователь №: 27 702



Цитата(jcxz @ Jun 30 2018, 10:21) *
Да я уже вчера всё сделал

Покажите пожалуйста выход генератора для случая DWORD, WORD, DWORD, BYTE, BYTE в виде asm-инструкций.
У меня с таблицей переменных и невыровненными данным получилось так
CODE
// r0 = *s, r1 = var
// DWORD[0]
68 0A - ldr r2, [r1, #0]
60 02 - str r2, [r0, #0]
// WORD[1]
89 0A - ldrh r2, [r1, #8]
80 82 - strh r2, [r0, #4]
// DWORD[2]
8A 0A - ldrh r2, [r1, #16]
80 C2 - strh r2, [r0, #6]
8A 4A - ldrh r2, [r1, #18]
81 02 - strh r2, [r0, #8]
// BYTE[6]
31 30 - add r1, #48
78 0A - ldrb r2, [r1, #0]
72 82 - strb r2, [r0, #10]
// BYTE[7]
7A 0A - ldrb r2, [r1, #8]
72 C2 - strb r2, [r0, #11]
30 0C - adds r0, #12
47 70 - bx lr


Кста, а есть у кого-нить справочник машинных кодов для Cortex-M всех семейств?
Не путать со справочником asm-команд, который найти не составляет труда.
Go to the top of the page
 
+Quote Post
jcxz
сообщение Jun 30 2018, 11:56
Сообщение #14


Гуру
******

Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713



Цитата(adnega @ Jun 30 2018, 11:59) *
Покажите пожалуйста выход генератора для случая DWORD, WORD, DWORD, BYTE, BYTE в виде asm-инструкций.

Да, как только поборю IAR. Если у Вас IAR, то как Вы ему сказали, чтобы он массив объявленный в программе как массив, показывал в окне дизасма как код? А то у меня он, собака, как только видит что это массив, показывает просто как кучу констант DC32 как этот массив не объявляй. Не могу заставить его дизассемблировать sad.gif(((
И мне не нужны байтовые операции - переменные только 16 и 32 бита.

Цитата(adnega @ Jun 30 2018, 11:59) *
Кста, а есть у кого-нить справочник машинных кодов для Cortex-M всех семейств?

Мне тоже хотелось-бы. Не нашёл в инете. Только если правильно выражаться: таблица маш.кодов набора инструкций Thumb-2.

Цитата(AlexandrY @ Jun 30 2018, 13:09) *
Господа, вы тут явно пытаетесь эмулировать DMA. biggrin.gif

Да причём тут DMA??? Каким боком он поможет в этой задаче? Разве чтобы только затормозить процедуру в несколько раз?

Цитата(AVI-crak @ Jun 30 2018, 14:24) *
Более простое название этого процесса - полиморфный код.

Мне без разницы как это называть. Пускай будет полиморфный.
А что именно требуется - мне кажется уже каждый должен был понять, хоть немного почитав тред.
Go to the top of the page
 
+Quote Post
adnega
сообщение Jun 30 2018, 12:12
Сообщение #15


Гуру
******

Группа: Свой
Сообщений: 2 724
Регистрация: 14-05-07
Из: Ярославль, Россия
Пользователь №: 27 702



Цитата(jcxz @ Jun 30 2018, 14:56) *
Да, как только поборю IAR.

gcc-шный objdump легко превращает бинарник в s-файл.
Можете скинуть бинарь - я его конвертну, если у вас нет gcc.
Go to the top of the page
 
+Quote Post
jcxz
сообщение Jun 30 2018, 13:30
Сообщение #16


Гуру
******

Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713



Цитата(adnega @ Jun 30 2018, 15:12) *
Можете скинуть бинарь - я его конвертну, если у вас нет gcc.

Спасибо, уже не надо - просто копировал из массива результат в неиспользуемую память МК, а для такой памяти IAR позволяет делать дизасм. Так и отладил.
Вобщем: всё ок работает алгоритм. rolleyes.gif
Ниже прикладываю результат его работы для 64-битного слова: 0000.002A.1003.0006.
При таких весах битов карты (см. установленные биты в бит-карте выше):
бит1=2 байта, бит2=2 байта, бит16=4 байта, бит17=2 байта, бит28=4 байта, бит33=4 байта, бит35=4 байта, бит37=2 байта.

Результат картинкой (не знаю как в IAR сохранить текстовое содержимое окна дизасма, а InqSoft Scaner не захватывает текст из этого окна):
Прикрепленное изображение

А здесь результат в бинарнике:
Прикрепленный файл  smk00.zip ( 233 байт ) Кол-во скачиваний: 4

Итого - время выполнения этого кода думаю будет == примерно 31 такт (не измерял), при условии что dst на входе - выровнен на 4.
Как можно догадаться: функция строится таким образом, чтобы она была определена как:
extern "C" void * Func(void *dst, u32 *table);
где: dst - буфер для записи (передаётся в R0); table - массив из 64-х указателей на захватываемые переменные.

Цитата(AlexandrY @ Jun 30 2018, 16:17) *
Скопирует все переменные в одну область и вышлет куда надо.
Или даже без копирования вышлет.

Ну-ну. А теперь объясните как он это скопирует, когда переменные разбросаны по всей памяти МК кусочками по 2 и по 4 байта? smile3009.gif
Про передачу свЯзными списками я в курсе.
Go to the top of the page
 
+Quote Post
AlexandrY
сообщение Jun 30 2018, 13:39
Сообщение #17


Ally
******

Группа: Модераторы
Сообщений: 6 232
Регистрация: 19-01-05
Пользователь №: 2 050



Цитата(jcxz @ Jun 30 2018, 16:30) *
Ну-ну. А теперь объясните как он это скопирует, когда переменные разбросаны по всей памяти МК кусочками по 2 и по 4 байта? smile3009.gif
Про передачу свЯзными списками я в курсе.

И чем не подошла передача связными списками?
Go to the top of the page
 
+Quote Post

Сообщений в этой теме
- jcxz   Самомодифицирующийся код в экосистеме Cortex-M.   Jun 28 2018, 22:54
- - aaarrr   Цитата(jcxz @ Jun 29 2018, 01:54) И вот я...   Jun 28 2018, 23:01
- - AVI-crak   Цитата(jcxz @ Jun 29 2018, 04:54) Просто ...   Jun 28 2018, 23:23
|- - aaarrr   Цитата(AVI-crak @ Jun 29 2018, 02:23...   Jun 28 2018, 23:31
||- - AVI-crak   Не предполагает. Любая перетасовка программного ко...   Jun 29 2018, 00:11
|- - Николай Семёнович   Цитата(AVI-crak @ Jun 29 2018, 02:23...   Jun 29 2018, 03:22
|- - jcxz   Цитата(AVI-crak @ Jun 29 2018, 02:23...   Jun 29 2018, 04:20
- - aaarrr   Давайте сначала: Цитата(AVI-crak @ Jun ...   Jun 29 2018, 00:32
|- - AVI-crak   Цитата(aaarrr @ Jun 29 2018, 06:32) О как...   Jun 29 2018, 04:47
|- - jcxz   Цитата(AVI-crak @ Jun 29 2018, 07:36...   Jun 29 2018, 04:51
||- - AVI-crak   Цитата(jcxz @ Jun 29 2018, 10:51) Вы о чё...   Jul 1 2018, 15:22
||- - VladislavS   Цитата(AVI-crak @ Jul 1 2018, 18:22)...   Jul 1 2018, 16:25
||- - jcxz   Цитата(VladislavS @ Jul 1 2018, 19:25) Пр...   Jul 2 2018, 16:12
||- - AVI-crak   Цитата(jcxz @ Jul 2 2018, 22:12) Конечно ...   Jul 2 2018, 20:46
||- - Arlleex   Цитата(AVI-crak @ Jul 3 2018, 00:46)...   Jul 3 2018, 04:44
||- - AVI-crak   Цитата(Arlleex @ Jul 3 2018, 10:44) А отк...   Jul 3 2018, 18:38
|- - aaarrr   Цитата(AVI-crak @ Jun 29 2018, 07:47...   Jun 29 2018, 07:24
- - halfdoom   Цитата(jcxz @ Jun 29 2018, 01:54) Есть мы...   Jun 29 2018, 03:29
|- - jcxz   Цитата(AlexandrY @ Jun 29 2018, 10:00) То...   Jun 29 2018, 07:03
||- - AlexandrY   Цитата(jcxz @ Jun 29 2018, 10:03) Ну хоро...   Jun 29 2018, 07:05
|- - Arlleex   Цитата(jcxz @ Jun 29 2018, 20:23) Всего в...   Jun 29 2018, 17:36
|- - AlexandrY   Цитата(adnega @ Jun 30 2018, 11:59) Кста,...   Jun 30 2018, 10:09
||- - jcxz   Цитата(AlexandrY @ Jun 30 2018, 16:39) И ...   Jun 30 2018, 13:56
||- - AlexandrY   Цитата(jcxz @ Jun 30 2018, 16:56) В то вр...   Jun 30 2018, 14:43
||- - jcxz   Цитата(AlexandrY @ Jun 30 2018, 17:43) Та...   Jun 30 2018, 19:41
||- - AlexandrY   Цитата(jcxz @ Jun 30 2018, 22:41) Ваш пос...   Jul 1 2018, 07:22
|- - AlexandrY   Цитата(jcxz @ Jun 30 2018, 14:56) Да прич...   Jun 30 2018, 13:17
- - Serge V Iz   Использовал хранимые в ОЗУ участки кода, которые з...   Jun 29 2018, 07:35
|- - jcxz   Цитата(Serge V Iz @ Jun 29 2018, 10:35) И...   Jun 29 2018, 08:43
- - AVR   Цитата(jcxz @ Jun 29 2018, 01:54) Есть мы...   Jun 29 2018, 07:43
|- - a123-flex   Цитата(AVR @ Jun 29 2018, 10:43) Оптимиза...   Jun 29 2018, 15:05
- - RadiatoR   Вопрос к ТС - а каков предполагаемый размер генери...   Jun 29 2018, 07:54
|- - _4afc_   Мой опыт показывает что оптимизация по скорости са...   Jun 29 2018, 08:23
|- - jcxz   Цитата(RadiatoR @ Jun 29 2018, 10:54) Во...   Jun 29 2018, 09:08
|- - _4afc_   Цитата(jcxz @ Jun 29 2018, 13:08) А тепер...   Jun 29 2018, 09:53
- - VladislavS   _4afc_, не стоит быть столь категоричным. Если гов...   Jun 29 2018, 08:38
- - Kabdim   Имхо сейчас время такое что проще взять более мощн...   Jun 29 2018, 08:44
- - Arlleex   Интересная тема для меня, тема СМК. Ни разу не при...   Jun 29 2018, 13:08
|- - RadiatoR   Цитата(Arlleex @ Jun 29 2018, 16:08) 2. Н...   Jun 29 2018, 13:23
|- - adnega   Цитата(Arlleex @ Jun 29 2018, 16:08) 1. П...   Jun 29 2018, 16:03
||- - Arlleex   Цитата(RadiatoR @ Jun 29 2018, 16:23) Та...   Jun 29 2018, 16:18
||- - adnega   Цитата(Arlleex @ Jun 29 2018, 19:18) Наде...   Jun 29 2018, 16:35
||- - Arlleex   Цитата(adnega @ Jun 29 2018, 19:35) Услов...   Jun 29 2018, 16:56
|- - jcxz   Цитата(Arlleex @ Jun 29 2018, 16:08) Прив...   Jun 29 2018, 16:56
||- - AlexandrY   Цитата(jcxz @ Jun 29 2018, 19:56) ... if ...   Jun 29 2018, 17:44
|- - kolobok0   Цитата(Arlleex @ Jun 29 2018, 16:08) Инте...   Jun 29 2018, 17:46
- - a123-flex   Цитата(jcxz @ Jun 29 2018, 01:54) Есть мы...   Jun 29 2018, 13:27
|- - twix   Цитата(a123-flex @ Jun 29 2018, 14:2...   Jun 29 2018, 14:35
- - Serge V Iz   Кстати, а какие есть основания предполагать, что р...   Jun 29 2018, 16:11
- - Arlleex   Цитата(AlexandrY @ Jun 29 2018, 20:44) А ...   Jun 29 2018, 18:19
- - AVI-crak   Цитата(jcxz @ Jun 29 2018, 04:54) Есть мы...   Jun 30 2018, 11:24
- - Arlleex   jcxz, а зачем тут это? Вы сначала загружаете адрес...   Jun 30 2018, 15:09
|- - jcxz   Цитата(Arlleex @ Jun 30 2018, 18:09) А вы...   Jun 30 2018, 19:31
|- - VladislavS   Цитата(jcxz @ Jun 30 2018, 22:31) Здесь н...   Jun 30 2018, 19:35
|- - Arlleex   Цитата(jcxz @ Jun 30 2018, 23:31) Поэтому...   Jun 30 2018, 19:45
|- - jcxz   Цитата(Arlleex @ Jun 30 2018, 22:45) По т...   Jun 30 2018, 19:54
- - VladislavS   Недавно в другой теме проскакивал вот такой код. П...   Jun 30 2018, 18:33
- - Arlleex   Кстати, решил почитать внимательнее 3.3.2. Load/st...   Jul 1 2018, 10:03
- - jcxz   Цитата(Arlleex @ Jul 1 2018, 13:03) Что э...   Jul 1 2018, 12:00


Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 20th June 2025 - 21:39
Рейтинг@Mail.ru


Страница сгенерированна за 0.01678 секунд с 7
ELECTRONIX ©2004-2016