Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Delphi: Общие вопросы > Дыры в Delphi


Автор: p0s0l 24.12.2003, 23:32
Щас буду коллекционировать глюки и недоделки в Delphi. А то обычно раз в месяц встречаюсь с какими-то непонятными глюками...

-------------------

Глюк:
Создаю новый проект, вытаскиваю Button, и пишу такое:
Код
label LabelEndOfProc;

procedure Proc1; assembler;
asm
 nop
 ret
 LabelEndOfProc:
end;

procedure TForm1.Button1Click(Sender: TObject);
begin
 asm
   mov eax, offset LabelEndOfProc
   push offset LabelEndOfProc
   sub eax, offset Proc1
 end;
end;

Попытка компиляции обламывается с Access Violation и дальше не работает клава в окне редактора...
Перезапуск Delphi или перезагрузка компа не влияют никак на успешность компиляции...

-------------------

Недоделка:
Тоже создаю новый проект и пишу:
Код
procedure Proc1;
begin
end;

function Func1 : Cardinal;
begin
 Dec (Result, Cardinal(@Proc1));
end;

На строке Dec выдается безымянная ошибка Internal C1030.

-------------------

Если бы я начал постить баги полгода назад, то, наверное, уже было бы страница или две... Щас только ничего вспомнить из того не могу...

Если что, тоже постите сюда баги...

Автор: zemfir 24.12.2003, 23:55
для таких случаев хорошо писать версию дельфиsmile.gif

Автор: p0s0l 25.12.2003, 00:03
Седьмая...

Автор: zemfir 25.12.2003, 00:12
ну дык, если планируется, что это кто-то будет использовать, то надо писать:

Delphi (полный номер версии)
билд такой-то
что установлено и т.п.
Операционная система такая-то
билд такой-то
глюк проявляется при таких-то условиях.
Проверен в таких-то условиях и т.п.

В общем стандартный баг репорт
smile.gif

Про ОС может и лишнее, но в остальном это нужно.

зы, какие-то Вы экстремальные вещи применяетеsmile.gif

Автор: Georg4 25.12.2003, 01:39
У меня был баг, если ты берешь из инета страницу через NMHTTP, а компьютер отключен от инета, виснет проект, а когда его отключаешь виснет дельфи, а когда её сбрасываешь, появляется системная ошибка експлорера

Автор: DonPager 27.12.2003, 21:55
Странно но:
Код

var
i,c: Byte;
A:array of array of Byte;
//---------
begin
SetLenght(A,10,10);
i := 10;
C := A[9,i];
end;

при этом не(!) возникает ошибки - почему confused.gif
при
Код

var
i,c: Byte;
A:array[0..9,0..9] of Byte;
//---------
begin
i := 10;
C := A[9,i];
end;

... при этом тоже нет ошибки, но при попытке C := A[9,10] - ошибка есть
... такое возникает только смногомерными..

Автор: <Spawn> 28.12.2003, 05:47
DonPager
Цитата
C := A[9,10]
Так элемента 10 не существует вот и ошибка. А в первом случае ты работаешь с динамическим массивом и вся ответственность по его управлению лежит на тебе. Компилятор сам не может проверить размер того массива. В данном случае не было ошибки, видимо, потому что данные лежащие по адресу DWORD(A) + 10 ни кем не использовались.

Автор: DonPager 28.12.2003, 11:07
<Spawn>
с динамическими я ещё смиряюсь, но почему нет ошибки когда
Код
var
i,c: Byte;
A:array[0..9,0..9] of Byte;
begin
i := 10;
C := A[9,i];
end;

вот для меня что самое обломное...

Автор: <Spawn> 28.12.2003, 13:00
А ты попробуй присвоить значение A[9, i] и будет тебе Access Violetion.

Автор: p0s0l 28.12.2003, 14:36
Цитата
var
i,c: Byte;
A:array[0..9,0..9] of Byte;
begin
i := 10;
C := A[9,i];
end;

Тут не должен по смыслу вылезать Access Violation, что при записи, что при чтении. Шанс исключения очень мал...
При приведенном выше чтении массива на самом деле будет читаться следующая переменная, стоящая за этим массивом.
Также, если включить опцию Range Checking {$R+}, то в коде при обращении к массиву через переменные будет сгенерирована проверка границ...

Вот примерчик еще:
Код
var
 i,c: Byte;
 A:array[0..9,0..9] of Byte;
 d : integer;

procedure TForm1.Button2Click(Sender: TObject);
begin
 FillChar(a, sizeof(a), 0);
 d := 55;
 i := 10;
 C := A[9,i]; // С будет равно 55
 C := A[i,0]; // С тоже будет 55
...
end;

Автор: Полудненко Олег 28.12.2003, 19:11
Спокойно, у меня при дебаги Квалификационного проекта (примерно 15000 строк кода) довольно часто на цилке в котором идёт исключительно присваиание различных переменных типа integer довольно часто выскакивает Синий экран смерти, или Делфа просто в мясо вешает всю систему...

Автор: dr.ZmeY 28.12.2003, 21:01
Бывает, что вешает кучу хинтов, будто бы глобальная переменная не используется... при чем ссылается на все места, все функции где я юзаю эту переменную...
smile.gif smile.gif smile.gif

Автор: DonPager 28.12.2003, 21:06
Цитата
А ты попробуй присвоить значение A[9, i] и будет тебе Access Violetion

вот если бы была ошибка - я бы не возмущался...
вместо ошибки в С идёт следуящая переменная.... в общем как и писал p0s0l...
а вот про {$R+} не знал...

Автор: MPak 29.12.2003, 22:03
Цитата(p0s0l @ 24.12.2003, 23:32)
Щас буду коллекционировать глюки и недоделки в Delphi. А то обычно раз в месяц встречаюсь с какими-то непонятными глюками...

-------------------

Глюк:
Создаю новый проект, вытаскиваю Button, и пишу такое:
Код
label LabelEndOfProc;

procedure Proc1; assembler;
asm
 nop
 ret
 LabelEndOfProc:
end;

procedure TForm1.Button1Click(Sender: TObject);
begin
 asm
   mov eax, offset LabelEndOfProc
   push offset LabelEndOfProc
   sub eax, offset Proc1
 end;
end;

Попытка компиляции обламывается с Access Violation и дальше не работает клава в окне редактора...
Перезапуск Delphi или перезагрузка компа не влияют никак на успешность компиляции...

-------------------

Недоделка:
Тоже создаю новый проект и пишу:
Код
procedure Proc1;
begin
end;

function Func1 : Cardinal;
begin
 Dec (Result, Cardinal(@Proc1));
end;

На строке Dec выдается безымянная ошибка Internal C1030.

-------------------

Если бы я начал постить баги полгода назад, то, наверное, уже было бы страница или две... Щас только ничего вспомнить из того не могу...

Если что, тоже постите сюда баги...

1)
Интересно конечно... я б на месте багланда
такие б программы не только не компилировал
а рекомендовал бы пойти программеру в школу
почитать чтонибудь из азов и теории компиляторов
чтобы не повадно бало мешать ассемблер с полным
непониманием принципов компиляции и оптимизатора

2)
в журнале Техника-Молодежи годов так 80-ых
были статьи как ушатать програмируемый калькулятор....
неудивительно что компилятор на порядки
более сложный чем ПК (калькулятор) ушатать тоже
можно.... вопрос в том - зачем програмировать
как попало и делать из себя вид очень умного,
а народ в багланде типа очень глупый.... сей пост только
показывает полную эквивалентность автора поста к
программерам багланда - чего ж ждать в результатеconfused.gif?

3)
Не стоит постить свои баги.... они по большому счету
не очень интересны....лучше почитать литературу ....
подучиться чтобы понять почему отквоченый бред,
а он таковой по определени и есть, не компилируется
нормально

Автор: MPak 29.12.2003, 22:09
Цитата(dr @ 28.12.2003, 21:01)
Бывает, что вешает кучу хинтов, будто бы глобальная переменная не используется... при чем ссылается на все места, все функции где я юзаю эту переменную...
smile.gif smile.gif smile.gif

А пример привести религия не позволяет?
Это так много чего можно написать
вплоть до того что у меня типа 2 + 2 = 5

Автор: Chingachguk 29.12.2003, 22:41
Цитата

1)
Интересно конечно... я б на месте багланда
такие б программы не только не компилировал
а рекомендовал бы пойти программеру в школу
почитать чтонибудь из азов и теории компиляторов
чтобы не повадно бало мешать ассемблер с полным
непониманием принципов компиляции и оптимизатора


А вот программерам, написавшим нечто, что допускает выполнения кода в стеке (переполнение буфера), как-то не получается порекомендовать пользователям "пойти поучиться в школе", а приходится быстро все чинить ;)

Не, ну я понимаю, что тут совсем другое дело. Компиллятор изначально позиционируется как прога, предназначенная для работы в "неагрессивной" обстановке, т.е. пользователи - нормальные люди, которые хотят скомпиллить свою программу а не завесить компиллятор любыми способами.

Как я понял, речь не о том, что "я вот счас круто написал тут лабуды и все красиво подохло". Речь о том, что случайная описка приводит к непонятным сообщениям, а, возможно, к перезапуску машины с риском потерять набранный код...

Вот я имею сейчас дело с одним си-компиллятором (txo). Эта норовистая штука. Достаточно написать "нестандартный" символ среди набранного текста из 10-50 строк в разных модулях как бац ! -не могу скомпиллировать и все. Никаких сообщений, ничего. Приходится последовательно откатываться. Или иногда описка (скажем, потеря "}") приводит к куче "полезных" сообщений с финальным "не хватает памяти чтобы вывести все ошибки". Тогда как в паскале (вроде и в дельфи, я не писал) компиллятор совершенно правильно останавливается на первой же синтаксической ошибке.

К тому же

Цитата
компилятор на порядки
более сложный чем ПК (калькулятор)


не так уж и беспомощен. Он имеет все шансы установить SEH и т.п.

Автор: p0s0l 29.12.2003, 23:28
Цитата
Интересно конечно... я б на месте багланда
такие б программы не только не компилировал
а рекомендовал бы пойти программеру в школу
почитать чтонибудь из азов и теории компиляторов
чтобы не повадно бало мешать ассемблер с полным
непониманием принципов компиляции и оптимизатора

Вот, Мрак, иди, пожалуйста, и учись, прежде чем тут гнуть пальцы.
Случаи, которые я приводил - из жизни - просто я урезал код до такой степени, чтобы не было лишнего, но чтобы глюк остался. Но изначально это был ОСМЫСЛЕННЫЙ код. Ты думаешь я сидел тут маразмом страдал, подбирал строки бессмысленные, чтобы вылез баг ? - Ошибаешься...

И причем ты тут про оптимизатор сказал ? Я что, должен еще заботиться, как бы тут оптимизатору туго не пришлось ?

Короче, если у тебя есть доводы - говори, а не швыряйся терминами. А то получается, что это про тебя: "Я знаю карате, айкидо, дзюдо ... и другие китайские слова!"...

Автор: Fantasist 30.12.2003, 03:11
Седьмая Делфи компилирует нормально следующий код:

Код


List.Add('Slovo',);




Обратите внимание на запятую после апострофа. Так работает везде где мы пробывали - в сочитании апостроф-запятая-правая скобка запятая игнорируется.

Автор: p0s0l 30.12.2003, 09:42
Fantasist - Прикольно! Я такого раньше не замечал...

Из этой же оперы - хотя это и не дырка, но смотрится немного странно:
Цитата
var a : array [0..3.) of integer;

.) = ]
(. = [

Автор: Петрович 30.12.2003, 11:04
Цитата
.) = ]
(. = [

Если мне не изменяет память, это пошло с очень древних времен, когда не во всех системах можно было ввести символы [ и ]. Вот и были придуманы метапоследовательности их заменяющие. Не знал что Delphi их еще поддерживает smile.gif

Автор: Мрак 7.1.2004, 01:02
Цитата

А вот программерам, написавшим нечто, что допускает выполнения кода в стеке (переполнение буфера), как-то не получается порекомендовать пользователям "пойти поучиться в школе", а приходится быстро все чинить ;)


Ну так кто ж тем прогаммерам виноват smile.gif

Цитата

Как я понял, речь не о том, что "я вот счас круто написал тут лабуды и все красиво подохло". Речь о том, что случайная описка приводит к непонятным сообщениям, а, возможно, к перезапуску машины с риском потерять набранный код...


Я понимаю что случайная описка валящая компилятор ни есть гуд. Но чтот в исходном сообщении я случайной описки не видел. Там было только агрессивное использования ассемблера с наглыми передачами управления и разрушением стека и наглое приведение типов с попыткой декрементировать полученное значение. Если второе с весьма большим натягом и можно назвать опиской то первое вообще ни в какие ворота не лезет. sad.gif

Цитата

не так уж и беспомощен. Он имеет все шансы установить SEH  и т.п.


Не имеет. Шансы имеет програмер. Но видимо такого никто не ожидал - видать не заложились smile.gif

Автор: МРак 7.1.2004, 01:17
Цитата
Вот, Мрак, иди, пожалуйста, и учись, прежде чем тут гнуть пальцы.


С этого места подробнее плз. Чему и у кого.

Цитата
Случаи, которые я приводил - из жизни - просто я урезал код до такой степени, чтобы не было лишнего, но чтобы глюк остался. Но изначально это был ОСМЫСЛЕННЫЙ код.


Осмысленный гришь... ну-ну.... заметно... что первый, что второй...
А для недоученных то есть меня можно пояснить сокровенный
смысл не того, что вырезано, а того что осталось. А то я уж совсем
плох withstupid.gif , видимо впрочем как и багланд, оказывается надо писать
он такие закорюки чтобы что-то работало да еще и на ассемблере,

Цитата

И причем ты тут про оптимизатор сказал ? Я что, должен еще заботиться, как бы тут оптимизатору туго не пришлось ?


Оптимизатор как раз к ассемблерным вставкам довольно хреного
относится. Причем в любом языке.



Автор: p0s0l 9.1.2004, 23:17
МРак, интересно, что приходится тут объяснять, как же получился такой код... Только когда я тебе расскажу смысл кода, ты мне скажешь, чем же это спасает ситуацию...

Смысл в том, что мне надо вычислить ТОЧНЫЙ размер кода процедуры Proc1.
Первоначальный вариант:
Код
procedure Proc1;
begin
.......
end;

function Proc1Len : Cardinal;
begin
  Result := Cardinal(@Proc1Len) - Cardinal(@Proc1);
end;

Этот способ мог давать погрешность до 3 байт, т.к. начало тел процедур выравнено по 4-байтной границе. А в ходе переборов разных вариантов набралось такое:
Код
procedure Proc1;
begin
end;

function Proc1Len : Cardinal;
begin
  Result := Cardinal(@Proc1Len);
  Dec (Result, Cardinal(@Proc1));
end;

Вылезает Internal Error. Смысл тот же самый, но не компилируется.
Уж извини меня, МРак, такого тупого программера, ведь только сел за Дельфи, а нигде не написано, как реализовать нужную мне задачу. Может ты мне скажешь, как же узнать размер процедуры, раз ты такой знаток Дельфей, компиляторов и асмов - это ведь тебе раз плюнуть, а мне придется мараться, глюки случайно находить то тут, то там, и я же буду, самое главное, виноват в этих глюках...

Короче, из-за неточности решил попробовать сделать через одно место. По смыслу метка - это адрес. Вот я и сделал так:
Код
label LabelEndOfProc;

procedure Proc1;
begin
// код здесь
  LabelEndOfProc:
end;

function Proc1Len : cardinal;
begin
  Result := Cardinal(@LabelEndOfProc) - Cardinal(@Proc1);
//  Result := Cardinal(LabelEndOfProc) - Cardinal(@Proc1); // тоже не работает
end;

Но так нельзя... Вот если бы ввели бы возможность узнавания адреса метки...
Ради эксперимента решил посмотреть, что будет, если:
Код
function Proc1Len : cardinal;
asm
  lea eax, [LabelEndOfProc - offset Proc1]
end;

Вот тут дельфи гнется, и окно редактора кода в дельфи становится глухим на нажатие кнопок.
Извиняюсь, МРак, конечно, за абсурдность идеи, видимо не дано быть мне программером, DVA мне это говорил, теперь ты говоришь...
Все, теперь буду трактористом. smile

В итоге я сделал вычисление размера процедуры по-трактористски:
Код

const
  SuperID = $12345678;
procedure Proc1; assembler;
asm
  la-la-la
  ret
  dd SuperID
end;

function Proc1Len : cardinal;
begin
  Result := Cardinal(@Proc1Len);
  while PCardinal(Result)^ <> SuperID do Dec(Result);
  Result := Result - Cardinal(@Proc1Len);
end;

Но опять же, так как это сделано по-трактористски, то не компилится (internal error)...
Найди разницу, МРак, и скажи, в чем принципиальное отличие, этот вариант компилится и работает:
Код
function Proc1Len : cardinal;
var a : Cardinal;
begin
  Result := Cardinal(@Proc1Len);
  while PCardinal(Result)^ <> SuperID do Dec(Result);
  a := Cardinal(@Proc1Len);
  Result := Result - a;
end;


Цитата
Оптимизатор как раз к ассемблерным вставкам довольно хреного
относится. Причем в любом языке.

И к чему ты это сказал ? Не использовать асм ? Спасибо! Или не использовать дельфи, а чисто асм ? Тоже спасибо!

А теперь, на десерт smile разбор такого вот изречения:
Цитата
Я понимаю что случайная описка валящая компилятор ни есть гуд. Но чтот в исходном сообщении я случайной описки не видел. Там было только агрессивное использования ассемблера с наглыми передачами управления и разрушением стека и наглое приведение типов с попыткой декрементировать полученное значение. Если второе с весьма большим натягом и можно назвать опиской то первое вообще ни в какие ворота не лезет.

Очень посмешил! smile
Цитата
с наглыми передачами управления

Хоть убей, но рыл-рыл, перерыл, но ниодной передачи управления так и не нашел!... А нет, что же я ? Ведь там есть такая процедура:
Procedure Proc1: nop ret
Возврат из процедуры - это передача управления! Притом наглая! Ведь до ret'а нет никаких осмысленных действий! Что это за процедура, которая ничего не делает? smile Хотя я наверное не говорил, что я УРЕЗАЛ код!
Цитата
разрушением стека

Ты можешь себе представить такое, что там в последствии была инструкция POP! Или ты забыл про такую команду, как POP, или я не написал, что код урезан ?
Цитата
наглое приведение типов

Какой же я наглец! Привести pointer к cardinal - это не по-программерски! Это нагло, по-ламерски, и вообще ерунда какая-то!
Цитата
с попыткой декрементировать полученное значение

Dec от слова Decrement, ты абсолютно прав. Но ты забыл сказать, что это НАГЛАЯ попытка декремента! smile А в дельфи можно декрементировать/инкрементировать целочисленные переменные, в данном случае - cardinal. Cardinal - это 4 байта, в байте 8 бит, бит - это 0 или 1... К чему это все ? smile

Короче, МРак, спасибо, что объяснил построчно, что же я там накалякал.

Цитата
Не имеет. Шансы имеет програмер. Но видимо такого никто не ожидал - видать не заложились

Да... Куда уж мне, бесталантному трактористу-програмисту-самоучке тягаться с таким титаном программирования, как МРак, который своим зорким взором смотря вдаль (правда не слыша, что ему кричат в упор) сразу выцепил из толпы "ламака" (т.е. меня).

Цитата
вопрос в том - зачем програмировать
как попало и делать из себя вид очень умного,
а народ в багланде типа очень глупый.... сей пост только
показывает полную эквивалентность автора поста к
программерам багланда - чего ж ждать в результате

По-моему, вывод один - тут есть только один индивид (МРак), который строит из себя супер-программера, которому влом объяснять азы тупым программерам (таким же тупым как и Борландовцы?), типа меня (p0s0l).

Про тупость Борланда - это твои слова. Я без всякого злого умысла выложил то, что накопал (найди хоть слово в адрес дельфи или Борланда), никак не думая, что найдется умник МРак, и начнет говорить, что код абсурдный, противоречит всем законам физики и т.д. Но тема-то создана для сбора глюков. Но никак не для спора на темы о правильности писания кода. Неважно, правильно я сделал, или нет, написав ту лажу-нелажу, но главное, что Дельфи от этого не защищен.

Особенно интересуют Internal Error-ы. Например, помню был случай, когда прогал то ли на D5, то ли на D6. И там писал процедурину, где было два вложенных цикла, в циклах - пара вложенных условий, пара case'ов, короче, такая вложенность begin..end'ов. Вставил break, да не туда, получилось вне цикла. При компиляции выдавалось что-то вроде Internal Error, но курсор на строку с break'ом не ставился.
Потерял полчаса прежде чем догадался, что дело было в Break. (Умный МРак скажет - тупой программер, вот так долго и искал...). Вот, теперь (В D7) эта ошибка уже проименована, и догадаться в чем дело не составляет труда...
И поэтому, МРак, не вижу ничего плохого в том, чтобы говорить об ошибках в Delphi, может, это кому-то поможет, и может, это кому-то интересно.

Короче, МРак, жду твоего ответа! Уж очень с тобой интересно общаться, настроение умеешь поднимать! smile

Автор: p0s0l 9.1.2004, 23:18
Уфф, не думал что столько выйдет! Долго не бывал на форуме - сказывается...

Автор: Полудненко Олег 9.1.2004, 23:47
ещё если после какого-нить опреатора стоит end, то после этого самого оператора можно не ставить ; и всё работает ОК:
Код

begin
showmessage('gluk')
end;

Автор: Fedor 10.1.2004, 00:37
Полудненко Олег Не понял... Ты думаешь, что это - глюк дельфи? На самом деле, это - не глюк, а наоборот возможность. Наоборот считается, что ";" - это отдельный оператор, и если его поставить перед end, то скорость работы программы уменьшится. Ненамного правда.

Автор: Петрович 10.1.2004, 21:50
По поводу ; перед end.
Дело в том, что язык Pascal лежащий в основе Delphi относится к языкам в которых символ ; является разделителем операторов. А поскольку end не является оператором, то и ; ставить перед ним нет надобности. А еще, в Pascal'е есть понятие пустой оператор, поэтому, можно ставить подряд несколько ;, ну и конечно ставить ; перед end. Причем замечу, наличие символов ; перед end, а так-же их количество на скорость работы программы не влияет. Достаточно взлянуть на код генерируемый компилятором.
А для справки, есть языки в которых символ ; служит символом завершающим оператор. В таких языках пропуск ; недопустим.

Автор: Fedor 11.1.2004, 00:27
Петрович Согласен. Я ошибался.

Автор: dm9 11.1.2004, 19:31
Насчёт ";":
был у меня как-то такой глюк в 5-х, то ли 6-х Делфях...
Стоял у меня перед end'ом оператор, после него точки с запятой не было. Программа не работала. После часа экспериментов до меня наконец дошло, что этот последний оператор компилятор не видит! Поставил точку с запятой - всё заработало. Теперь всегда ставлю ";" перед "end"...

Автор: Полудненко Олег 13.1.2004, 22:17
Ещё можно создавать переменные следующего вида integer:string; Тоесть давать имена переменным типа iteger, write и т.д.

Автор: Frikazoid 14.1.2004, 01:58
Код

function Proc1Len : Cardinal;
begin
Result := Cardinal(@Proc1Len);
Dec (Result, Cardinal(@Proc1));
end;

Я бы не стал так писать! У меня часто бывает, что операции с Result оканчиваются интернал еррором! т.е. по возможности надо пользовать доп. переменные и только по концухе Result:=....
Может я и ошибаюсь, но это ИМХО!

Автор: Петрович 14.1.2004, 03:29
Цитата
Может я и ошибаюсь, но это ИМХО!

И очень глубоко (прошу не рассматривать как наезд). Дело в том, что Result, это ни что иное как локальная переменная, содержимое которой возвращается как результат функции.
Сам я очень часто использую Result как локальную переменную. Вот пару примеров из моей библиотеки, которая работает у меня уже несколько лет:
Код
function RublesToText (N :Currency) : String;
begin
 Result := FormatFloat('.00',N);
 Result := Copy(Result,Pos('.',Result)+1,2);
 Result := Format('%s %s %s',[
                   NumberToText(N,tgMale,'рублей','рубль','рубля'),
                   Result,
                   Trail(StrToInt(Result),'копеек','копейка','копейки')
                   ]);
 Result[1] := AnsiUpcase(Result[1]);
end;

это совсем просто.
Код
function IndexOfStr (const S :String; Strings: array of string; const CaseSensitive: Boolean=True): Integer;
// Возвращает индекс строки S в массиве Strings. Если строка не найдена
// возвращает -1. Первая строка имеет индекс 0. Если CaseSensitive равно True
// то проверяется точное совпадение, иначе регистр символов игнорируется.
begin
 if CaseSensitive then begin
   for Result := Low(Strings) to High(Strings) do
     if S = Strings[Result] then Exit;
   end
 else begin
   for Result := Low(Strings) to High(Strings) do
     if awCompareText(S,Strings[Result]) = 0 then Exit;
 end;
 Result := -1;
end;

тут посложнее.
Ну и из совсем старых smile.gif
Код
function CenterCh(const S : string; Ch : Char; Len : Integer) : string;
{-Return a string centered in a string of Ch with specified width}
var SLen : Integer;
begin
 Result := S;  SLen := Length(S);
 if Len <= SLen then  Exit;
 SetLength(Result,Len);  FillChar(Result[1], Len, Ch);
 Move(S[1], Result[Succ((Len-SLen) shr 1)], SLen);
end;

Так что не сомневайтесь, а смело используйте.

Автор: p0s0l 14.1.2004, 12:17
Frikazoid, даже сам Borland частенько юзает Result как обычную переменную...
Загляни в SysUtils или StrUtils...
Вот пример: (из StrUtils)
Цитата
function SoundexWord(const AText: string): Word;
var
  LResult: string;
begin
  LResult := Soundex(AText, 4);
  Result := Ord(LResult[1]) - Ord('A');
  Result := Result * 26 + StrToInt(LResult[2]);
  Result := Result * 7 + StrToInt(LResult[3]);
  Result := Result * 7 + StrToInt(LResult[4]);
end;

Автор: Frikazoid 14.1.2004, 13:21
Сори перепутал с паскалем! smile.gif

Автор: p0s0l 14.1.2004, 13:24
Цитата
Ещё можно создавать переменные следующего вида integer:string; Тоесть давать имена переменным типа iteger, write и т.д.

Нельзя использовать в качестве имен зарезервированные слова типа case, string, короче которые жирным пишутся.
Про типы: интересно, почему string - зарезервированное слово, а byte, integer, word, boolean, real, pointer и др. типы - нет ?

Автор: Петрович 14.1.2004, 18:14
Цитата
Сори перепутал с паскалем!

smile.gif Дык в паскале переменной Result небыло, а жаль, очень не хватало.

Автор: December 14.1.2004, 23:21
Цитата
интересно, почему string - зарезервированное слово, а byte, integer, word, boolean, real, pointer и др. типы - нет ?
Каждый раз, когда смотрю на жирный стринг, об этом думаю. smile.gif

Автор: stab 14.1.2004, 23:31
Цитата(December @ 14.1.2004, 20:21)
Цитата
интересно, почему string - зарезервированное слово, а byte, integer, word, boolean, real, pointer и др. типы - нет ?
Каждый раз, когда смотрю на жирный стринг, об этом думаю. smile.gif


Аналогично... было бы круто если бы можно было писать:

Код

var
 var1: string of Int64;


может это и было в планах у Борланд? hehe.gif

Автор: p0s0l 15.1.2004, 07:10
Цитата(cully @ 14.1.2004, 23:31)
Цитата(December @ 14.1.2004, 20:21)
Цитата
интересно, почему string - зарезервированное слово, а byte, integer, word, boolean, real, pointer и др. типы - нет ?
Каждый раз, когда смотрю на жирный стринг, об этом думаю. smile.gif


Аналогично... было бы круто если бы можно было писать:

Код

var
 var1: string of Int64;


может это и было в планах у Борланд? hehe.gif

cully, вот ты почти и ответил... Integer и др. типы - простые типы, ничего кроме имени типа не надо указывать. А у стринга можно еще длину указывать...

Автор: Mpak 18.1.2004, 03:57
Цитата
МРак, интересно, что приходится тут объяснять, как же получился такой код... Только когда я тебе расскажу смысл кода, ты мне скажешь, чем же это спасает ситуацию...

Смысл в том, что мне надо вычислить ТОЧНЫЙ размер кода процедуры Proc1.
Первоначальный вариант:
Код
procedure Proc1;
begin
.......
end;

function Proc1Len : Cardinal;
begin
 Result := Cardinal(@Proc1Len) - Cardinal(@Proc1);
end;

Этот способ мог давать погрешность до 3 байт, т.к. начало тел процедур выравнено по 4-байтной границе.


Остальные извращения с инструментом не предназначенным для системного программирования покипаны.

Всего пара глупых вопросов
1. На кой его знать точно? С чего вдруг погрешность от выравнивания стала критична?
2. На кой это нужно определять в рантайме?






Автор: p0s0l 18.1.2004, 13:18
2. На кой это нужно определять в рантайме? [/QUOTE]

Цитата
2. На кой это нужно определять в рантайме?

На той, что при компиляции никак не узнать размер. А если вначале засунуть это в константу, то будет не то, т.к. эту процедуру я меняю часто, и каждый раз переузнавать размер как-то в лом.

Цитата
Всего пара глупых вопросов
1. На кой его знать точно? С чего вдруг погрешность от выравнивания стала критична?

Мрак, как видно, ты и дальше пытаешься лезть в дебри... Вот глупый вопрос - а зачем тебе знать это ?
Разве это что-то изменит ? У меня была такая задача, и всё, неважно, зачем это нужно было. Но это было нужно. Точка.

Цитата
Остальные извращения с инструментом не предназначенным для системного программирования покипаны.

Ну-ну... В книжке, наверное, вычитал словечки "Компилятор", "Оптимизатор", "Системное программирование" ? Продолжай в том же духе.

Автор: Guest 18.1.2004, 20:25
Цитата
Цитата

2. На кой это нужно определять в рантайме?

На той, что при компиляции никак не узнать размер. А если вначале засунуть это в константу, то будет не то, т.к. эту процедуру я меняю часто, и каждый раз переузнавать размер как-то в лом.


Ясно. Про MAP файлы никто не слышал.....

Цитата

Цитата
Всего пара глупых вопросов
1. На кой его знать точно? С чего вдруг погрешность от выравнивания стала критична?

Мрак, как видно, ты и дальше пытаешься лезть в дебри... Вот глупый вопрос - а зачем тебе знать это ?
Разве это что-то изменит ? У меня была такая задача, и всё, неважно, зачем это нужно было. Но это было нужно. Точка.


Тоже ясно. Как ... задача была сформулирована так .... она и решается.
Пропущеный наречия по тексту каждый волен расставить сам.

Вот бы всеж узнать на кой. А то кроме хакерского пальцегнутия и
представить то не могу ЗАЧЕМ в дельфях узнавать размер
процедуры, с точностью до байта, да еще и такими способами.

Цитата
Цитата
Остальные извращения с инструментом не предназначенным для системного программирования покипаны.

Ну-ну... В книжке, наверное, вычитал словечки "Компилятор", "Оптимизатор", "Системное программирование" ? Продолжай в том же духе.


Ну я хоть читаю... Мне хоть не стыдно за свой код.

smile.gif


Автор: p0s0l 23.1.2004, 19:41
Ладно, Мрак, высказывание про map-файлы (и некоторые другие предыдущие моменты) поставило точку в определении твоего истинного уровня знаний:
map-файле Delphi, как ты мог бы заметить, если бы хоть раз их видел в живую, а не в умной книжке, не указан размер процедуры, а указан только адрес... Увы...

Других способов решения моей задачи ты не представил, а только допытываешься до вопроса: зачем это надо ?
Короче продолжать это бессмысленно.

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)