![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Изменить VMT
DevilDevil © (2007-07-23 10:20:00)Как бы то ни было странно, пишу такую функцию, типа PatchSomeClass(C : TClass) в теле которой происходит "подмена" адреса одной виртуальной функции.
Как я себе это представляю.
Для каждого класса существует некий массив указателей на функции (VMT). В каждом экземпляре такого класса хранится указатель на массив-VMT. Следовательно, получив указатель на VMT, зная смещение, я могу записать в этот массив произвольный указатель на функцию.
Все мои опыты приводят к AccessViolation. Есть ли какие нибудь предположения или наработки по данному поводу?
Инс (2007-07-24 10:16:00) [21]
> Либо сам удалишь, вызвав DeleteObjects в нужный момент,
> либо он всё равно вызовется при finalization.
А какой смысл освобождать память под экземпляр при завершении приложения? Когда процесс завершается система и так освобождает всю занятую им память. Разве что если в деструкторе выполняется какое-либо сохранение данных в файл или еще что-то в этом роде. А вот с интерфейсами все интереснее - объект финализируется когда выходит за область видимости. Другими словами, память будет освобождена не просто автоматически, но еще и сразу же, как в объекте отпадет необходимость.
Сергей М. (2007-07-24 08:15:00) [22]
> DevilDevil © (23.07.07 17:45) [26]
> представь глобальную переменную - интерфейс. Если ты её
> не удалишь, она сама удалится
И что ?
DevilDevil (2007-07-23 19:13:00) [23]
procedure DeleteObjects();
цикл по всем объектам
ARR[i].Free;
finalization
DeleteObjects();
Либо сам удалишь, вызвав DeleteObjects в нужный момент, либо он всё равно вызовется при finalization.
в "конструкторе" объект добавляет себя в массив
в "деструкторе" объект удаляет себя из массива
Инс (2007-07-23 19:11:00) [24]Из-за неправильного употребления Вами терминов я ничего не понял:
> в случае чего будут сами удаляться (finalization)...
> во-вторых, которые можно было бы удалить всего одной функцией....
Кто удаляться? Классы или экземпляры классов? Если второе, то они и так удаляются вызовом одного метода - Free. А интерфейсы зря недооцениваете - там вам и подобие множественного наследования (можно еще на директиву implements глянуть) и горизонтальный полиморфизм, и автоматическая финализация. Плюс действительно class helper - достаточно мощная вещь, может стоит подумать о переходе на новые версии. Но все же меня терзают смутные сомнения в целесообразности сего действия. Мне как-то всегда возможностей классического ООП хватало.
oxffff (2007-07-23 18:33:00) [25]
> Хочется мне сделать некий менеджер объектов классов, которые
> во-первых, в случае чего будут сами удаляться (finalization),
> во-вторых, которые можно было бы удалить всего одной функцией.
>
Так финализация или удаление?
>Для этого был создан мой класс, вышеупомянутые методы которого >используются для добавления и удаления себя из буффера объектов.
Newinstance и FreeInstance?
DevilDevil (2007-07-23 17:46:00) [26]> Rouse_ © (23.07.07 17:45) [25]
да боюсь я пока на новые версии переходить.
и так справлюсь. :)
DevilDevil (2007-07-23 17:45:00) [27]> Сергей М. © (23.07.07 17:03) [23]
представь глобальную переменную - интерфейс. Если ты её не удалишь, она сама удалится.
А вот если ты разрабатываешь класс-текстуру, то все объекты этого класса нужно будет удалить прежде, чем будет удалён контекст устройства.
> umbra © (23.07.07 17:26) [24]
Попробуй наследоваться, скажем, от TComponent и TStream
Rouse_ (2007-07-23 17:45:00) [28]Мошт тебе на 2007-ую перейти, там хелперы для расширения возможностей базовых классов есть...
umbra (2007-07-23 17:26:00) [29]О! Множественное наследование в Делфи. Это круто.
Сергей М. (2007-07-23 17:03:00) [30]
> объектов .. которые во-первых, в случае чего
> будут сами удаляться
Это как это ?
DevilDevil (2007-07-23 17:00:00) [31]oxffff, круто, попробую сегодня!
> Сергей М. © (23.07.07 15:06) [16]
> Инс © (23.07.07 15:29) [17]
> Игорь Шевченко © (23.07.07 15:31) [18]
Ну... как сказать...
Хочется мне сделать некий менеджер объектов классов, которые во-первых, в случае чего будут сами удаляться (finalization), во-вторых, которые можно было бы удалить всего одной функцией.
Многие сейчас захотят сказать "наследуйся от интерфейса"... но это не совсем то, что мне нужно.
Для этого был создан мой класс, вышеупомянутые методы которого используются для добавления и удаления себя из буффера объектов.
Для того, чтобы "воспользоваться" таким классом нужно просто пронаследовать новый класс от этого.
Но, чтобы модуль был полноценным, хочу написать такую функцию, которая могла бы пропатчить не просто экземпляр класс, а целый класс. К примеру, если я буду писать компонент с такой особенностью, то я вроде бы не смогу пронаследовать его одновременно от 2х классов: от TComponent и моего класса. Ну или нужно "пропатчить" имеющийся класc, TStream, например.
Реальной какой-то пользы от такой функции я не жду ... , но:
1) интересно написать такую функцию
2) она может понадобиться
oxffff (2007-07-23 16:03:00) [32]Поправь на
procedure Myproc(Obj:Tobject);
var a:string;
begin
a:=obj.ClassName;
Messagebox(0,pchar(A),pchar(A),0);
asm
mov eax,obj;
call old;
end;
end;
oxffff (2007-07-23 15:55:00) [33]var
Form1: TForm1;
Old:Pointer;
implementation
uses Math;
{$R *.dfm}
procedure Myproc(Obj:Tobject);
var a:string;
begin
a:=obj.ClassName;
Messagebox(0,pchar(A),pchar(A),0);
asm
call old;
end;
end;
procedure TForm1.Button1Click(Sender: TObject);
var ClassType:TClass;
a:pointer;
OldFlags:DWORD;
begin
ClassType:=Tbutton;
VirtualProtect(ClassType,4096,PAGE_EXECUTE_READWRITE,OldFlags);
a:=@Myproc;
asm
push eax;
push ebx;
mov eax,a;
mov ebx,ClassType;
lea ebx,[ebx-$1C];
xchg [ebx],eax;
mov old,eax;
pop ebx;
pop eax;
end;
FlushInstructionCache(HInstance,nil,0);
with TButton.Create(nil) do parent:=self;
end;
oxffff (2007-07-23 15:50:00) [34]Сейчас тебе пример напишу. :)
Игорь Шевченко (2007-07-23 15:31:00) [35]
> вообще хочется "подменить" методы BeforeDestucturing и AfterConstuction
> <-- как это очень похоже они называются. Их смещения отрицательные.
> Вряд ли сменятся.
А переопределить методы в наследниках что мешает ? Они же виртуальные.
Инс (2007-07-23 15:29:00) [36]
> BeforeDestucturing и AfterConstuction
Я таких не знаю ;)
А если серьезно, то у меня такое подозрение, что Вы просто неверно спроектировали структуру классов, вот теперь и изворачиваетесь. Может просто пересмотреть структуру?
Сергей М. (2007-07-23 15:06:00) [37]
> вообще хочется "подменить" методы BeforeDestucturing и AfterConstuction
А с чем связано рождение этой блажи ?
DevilDevil (2007-07-23 15:04:00) [38]вообще хочется "подменить" методы BeforeDestucturing и AfterConstuction <-- как это очень похоже они называются. Их смещения отрицательные. Вряд ли сменятся.
Инс (2007-07-23 14:41:00) [39]Это я к чему... Если планируется таким образом подменить в VMT ссылку на конкретный метод конкретного класса, а в будущих версиях структура этого класса изменится и адрес метода окажется по другому смещению, то можно нарваться на неприятность. Хотя допускаю, что если не использовать непосредственно цифровые значения смещений, то может и получится.
umbra (2007-07-23 14:29:00) [40]
> Только эта ваша функция на других версиях Delphi может не
> работать
если обращаться только по неотрицательным смещениям в вмт, то должна работать во всех версиях, где можно создавать СОМ-объекты