Здравствуйте, гость ( Вход | Регистрация )

 
Ответить в эту темуОткрыть новую тему
> Lua number -> pointer cast
Cockney
сообщение 5.11.2019, 13:16
Сообщение #1


********

Master
Сообщений: 1.394
Регистрация: 22.6.2013
Группа: Пользователи
Наличность: 20893
Пользователь №: 16.156



Вопрос знатокам.

Есть ffi.cdef

Код

    struct image_descriptor {
           unsigned char* address;
           int width;
           int height;
           int length;
    };


далее

Код
local a,w,h,l = getimage()

local img_descr = ffi.cast("struct image_descriptor*")
img_descr.address = a


Получаем ошибку. Собственно, на сколько я понял, в документации написано : только number -> number, pointer -> pointer, иные варианты не допустимы.

Как выкручиваться ?
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
DarkMaster
сообщение 5.11.2019, 15:01
Сообщение #2


***********

Модератор UOPilot
Сообщений: 9.460
Регистрация: 2.12.2008
Группа: Супермодераторы
Наличность: 27708
Пользователь №: 11.279



Потому что ты указателю присваиваешь строку. Не по адресу указателя, а в сам указатель.


--------------------
Скрипты UOPilot под заказ.
Консультации по UOpilot 15$/час.
Услуги Lua разработчика (не пилот, проекты, постоянка)
Disсоrd:
Kov____
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
Cockney
сообщение 5.11.2019, 18:49
Сообщение #3


********

Master
Сообщений: 1.394
Регистрация: 22.6.2013
Группа: Пользователи
Наличность: 20893
Пользователь №: 16.156



Какая строка ? Getimage возвращает address как строку ? Так или иначе, можно правильный код ?
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
DarkMaster
сообщение 6.11.2019, 2:37
Сообщение #4


***********

Модератор UOPilot
Сообщений: 9.460
Регистрация: 2.12.2008
Группа: Супермодераторы
Наличность: 27708
Пользователь №: 11.279



Вот тебе оно реально надо с типами мозг насиловать? Любой указатель есть int.
Код

ffi.cdef[[
    typedef struct {
           int address;
           int width;
           int height;
           int length;
    } image_descriptor;
]]

local a,w,h,l = getimage(100,100,220,220)

local img_descr = ffi.new("image_descriptor")

img_descr.address = a


Сообщение отредактировал DarkMaster - 6.11.2019, 2:37


--------------------
Скрипты UOPilot под заказ.
Консультации по UOpilot 15$/час.
Услуги Lua разработчика (не пилот, проекты, постоянка)
Disсоrd:
Kov____
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
Cockney
сообщение 6.11.2019, 22:12
Сообщение #5


********

Master
Сообщений: 1.394
Регистрация: 22.6.2013
Группа: Пользователи
Наличность: 20893
Пользователь №: 16.156



в частном случае - да, но тем не менее, сам факт такого костыля...искажает суть написанного, если писал не ты.
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
DarkMaster
сообщение 14.11.2019, 12:05
Сообщение #6


***********

Модератор UOPilot
Сообщений: 9.460
Регистрация: 2.12.2008
Группа: Супермодераторы
Наличность: 27708
Пользователь №: 11.279



Я не сомневаюсь, что можно сделать нормально, но тут уж я виноват - всегда непереносил С за переименование базовых типов.


--------------------
Скрипты UOPilot под заказ.
Консультации по UOpilot 15$/час.
Услуги Lua разработчика (не пилот, проекты, постоянка)
Disсоrd:
Kov____
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
Cockney
сообщение 14.11.2019, 15:39
Сообщение #7


********

Master
Сообщений: 1.394
Регистрация: 22.6.2013
Группа: Пользователи
Наличность: 20893
Пользователь №: 16.156



Си здесь не причем. Тут нет никакого переименования типов. Например, unsigned char есть по сути тип byte, т.е. аллиас. А что ты предложил - просто каст любого числа, и не просто любого, а знакового, к поинтеру(он же uintptr_t, uint32_t). Т.е. в том int может лежать -1 и это спокойно уйдет в длл, где воспримется как невалидный поинтер. Можно еще вспомнить про размер указателя, но это не так опасно как описанное выше.
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
DarkMaster
сообщение 14.11.2019, 16:38
Сообщение #8


***********

Модератор UOPilot
Сообщений: 9.460
Регистрация: 2.12.2008
Группа: Супермодераторы
Наличность: 27708
Пользователь №: 11.279



А указателю ты =1 не присвоишь? Что-то мне подсказывает, что он все-таки обычный инт а не unsigned, ибо на 32 битах ограничение 2гб, а не 4. Если не присвоишь, то это вопрос доб оберток и safe функций. Ну типа круто, все такое, но в моем понимании, если ты лезешь писать на Си, то ты должен понимать, что делаешь и как ты вообще допустил туда -1. Для меня все-таки (пусть это с точки зрения терминологии ппц ваще как не правильно) обычное переименование, алиас или еще что-то. Если значение в памяти занимает одинаковое количество байт и способ записи не меняется, а названий (способов объявления) много, то для меня это становится некоторым сомнительным решенем, особенно когда вызывает конфликты кастов при том, что в памяти эти "разные" типы выглядят идентично. Не фанат я таких решений. Для меня это сокрытие от пользователя природы вещей и дистанцирование от базы. Все выше описанное личное мнение и не более того.

Сообщение отредактировал DarkMaster - 14.11.2019, 16:40


--------------------
Скрипты UOPilot под заказ.
Консультации по UOpilot 15$/час.
Услуги Lua разработчика (не пилот, проекты, постоянка)
Disсоrd:
Kov____
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
Cockney
сообщение 14.11.2019, 17:03
Сообщение #9


********

Master
Сообщений: 1.394
Регистрация: 22.6.2013
Группа: Пользователи
Наличность: 20893
Пользователь №: 16.156



Цитата
А указателю ты =1 не присвоишь?


Именно 1? Присвою ,конечно, только он все равно не валидный. Вообще история с signed/unsigned для того, чтобы благополучно получить эксепшн(ошибку компиляции) в ходе арифметики с указателями, а не лезть сразу по отрицательному.


Цитата
если ты лезешь писать на Си, то ты должен понимать, что делаешь и как ты вообще допустил туда -1


А вот и нет. Сама система типов не даст без явных кастов пропихнуть -1 как адрес. Получишь минимум ворнинг. А вот в int, который уже в моей длл будет выглядеть как поинтер - пожалуйста.

Т.е. в идеале в скрипте нельзя указателю присвоить -1 и в длл тоже нельзя. Получим то что хотели, а щас я могу лишь надеться(написать обертку) что данные валидные.

Цитата
Если значение в памяти занимает одинаковое количество байт и способ записи не меняется а названий (способов объявления) много, то для меня это становится некоторым сомнительным решенем, особенно когда вызывает конфликты кастов при том, что в памяти эти "разные" типы выглядят идентично


Как int32 может быть равен uint32 ? И там и там 4 байта, диапазоны разные, а уж инструкции для работы с ними тем более. Так например, побитовый сдвиг для signed сохраняет знаковый бит, а для unsignned - нет. Тоже сложение, для одного результатом может стать переполнение, для другого просто неверный результат. Таких отличий - море. Другой вопрос, когда появляются аллиасы UINT, UINT32, DWORD, QWORD и так далее, вот тут уже перебор.


К слову, для ясности, int, unsigned int - фундаментальные типы, т.е. априори они не одно и тоже. int32_t и uint32_t лишь удобные аллиасы для них. а вот DWORD(uint32) уже аллиас, который не нужен.
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
DarkMaster
сообщение 14.11.2019, 17:51
Сообщение #10


***********

Модератор UOPilot
Сообщений: 9.460
Регистрация: 2.12.2008
Группа: Супермодераторы
Наличность: 27708
Пользователь №: 11.279



Цитата
Именно 1?

Шифт. -1 естественно. У меня студии под рукой нет. Мне прям интересно даст ли присвоить именно на стадии компиляции -1 указателю.
Цитата
А вот и нет. Сама система типов не даст без явных кастов пропихнуть -1 как адрес. Получишь минимум ворнинг. А вот в int, который уже в моей длл будет выглядеть как поинтер - пожалуйста.

Вот есть как раз подозрение, что это как максимум. Не уверн в том, что будет ошибка компиляции и совсем не уверен будет ли хоть какая-то разница в бинарнике.
Цитата
К слову, для ясности, int, unsigned int - фундаментальные типы, т.е. априори они не одно и тоже.

Я с Сями хоть и на вы, но не настолько же) Уж как в памяти это выглядит я себе представляю и там разница в одном бите который определяет знак либо значение разряда в зависимости от типа.
Я не говорю, что это одно и то же, я говорю о том, что, как я помню указатель является int'ом, а не uint'ом, т.к. ограничение по диапазону значений соответсвует int, так же учитывая скорость обработки знаковых и беззнаковых типов намекает на то, что делать указатель беззнаковым типом к большой потере производительности. Это одна из причин, почему я очень сильно сомневаюсь в получении эксепшена в откомпиленной программе и ворнинг компилятора скорее все, что мы получим (речь естественно о присвоении, а не про обращение по адресу).

Цитата
К слову, для ясности, int, unsigned int - фундаментальные типы, т.е. априори они не одно и тоже.

Так же речь была именно про одинаковые в памяти вещи. Самый поверхностный вариант ты уже привел - byte. Можно еще открыть winapi и посмотреть какая там радость наворочена. Достаточно вспомнить отсылку сообщений когда отсылаются два параметра по два байта. Беззановые. Думаешь unsigned word там будет?) И так со всем.

Сообщение отредактировал DarkMaster - 14.11.2019, 17:43


--------------------
Скрипты UOPilot под заказ.
Консультации по UOpilot 15$/час.
Услуги Lua разработчика (не пилот, проекты, постоянка)
Disсоrd:
Kov____
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
Cockney
сообщение 14.11.2019, 22:48
Сообщение #11


********

Master
Сообщений: 1.394
Регистрация: 22.6.2013
Группа: Пользователи
Наличность: 20893
Пользователь №: 16.156



Цитата
Мне прям интересно даст ли присвоить именно на стадии компиляции -1 указателю.



Если в тупую - void* memPtr = -1, то не даст, невозможно кастануть int к void*. Если явно - void* memPtr = (void*)-1, то -1 приведет к max uint64, что странно, ибо компилировал под x32, но так или иначе, -1 превращается в верхнюю границу типа.

Цитата
как я помню указатель является int'ом, а не uint'ом


Если исходить из того, что в машине нельзя обращаться по отрицательным адресам (а int подразумевает хранение таковых) он конечно может быть указателем но на определенном диапозоне, пусть даже и совпадает от 0 до max с максимальным адресом системы, но в качестве безопасности интерфейса общения разных интерфейсов я бы лично использовал uint для этого. В качестве отступления : в c++11 есть два типа указателей intptr_t и uintptr_t, для чего - написано где-то в стандарте

Впервые слышу, чтобы знак как-то влиял на производительность.

Цитата
winapi


winapi - не си, там своя атмосфера и "особый путь".

Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения

Ответить в эту темуОткрыть новую тему
10 чел. читают эту тему (гостей: 10, скрытых пользователей: 0)
Пользователей: 0

 

- Текстовая версия | Версия для КПК Сейчас: 28.3.2024, 21:04
Designed by Nickostyle