Справочник функций

Ваш аккаунт

Войти через: 
Забыли пароль?
Регистрация
Информацию о новых материалах можно получать и без регистрации:

Почтовая рассылка

Подписчиков: -1
Последний выпуск: 19.06.2015

Маленький размер проги

1.9K
15 сентября 2004 года
ProgMaster
47 / / 29.08.2004
Как сделать максимально маленький размер проги, без использования АПИ, но с использованием СОМ функций. Т.е. чтобы прога работала. Окна проге не нужны.
Вообщем какой тип проекта выбрать, и что в настройках изменить ?


PS: размер одиночного *.ехе файла должен быть не больше 100кб. ВОоще такое возможно та ?
6.3K
18 сентября 2004 года
Denri
43 / / 12.08.2004
Минимальная (в принципе) прога получится из такого исходника:
#---------------------------
#include <windows>
DWORD APIENTRY start(VOID){
return EXIT_SUCCESS;
}
#---------------------------
Размер от 496 байт. :)
В настройках проекта надо установить Linker -> Advanced -> Entry Point = "start" (/ENTRY:start). Если не использовать библиотеки вроде STL, ATL, MFC и т. д., то получится намного меньше 100 кб. :)
3
18 сентября 2004 года
Green
4.8K / / 20.01.2000
Цитата:
Originally posted by Denri
Минимальная (в принципе) прога получится из такого исходника:
#---------------------------
#include <windows>
DWORD APIENTRY start(VOID){
return EXIT_SUCCESS;
}
#---------------------------
Размер от 496 байт. :)
В настройках проекта надо установить Linker -> Advanced -> Entry Point = "start" (/ENTRY:start). Если не использовать библиотеки вроде STL, ATL, MFC и т. д., то получится намного меньше 100 кб. :)



Размер исполняемого файла PE не может быть меньше 1кб.

Кстати, зачем ты подключаешь windows.h ?
Да и для чего нужна такая программа? Программа должна что-то делать, хотя бы выводить "Hello world!", при этом она не превысила бы 1кб:
http://forum.codenet.ru/showthread.php?threadid=16213

Смотри статью здесь:
http://www.codenet.ru/progr/visualc/esmall.php

6.3K
19 сентября 2004 года
Denri
43 / / 12.08.2004
>> Размер исполняемого файла PE не может быть меньше 1кб.
Я же сказал 496. Работает нормально, но, действительно, ничего не делает. :)

>> Кстати, зачем ты подключаешь windows.h ?
Можно и без .h, если С++... Любая прога под винду его использует, да и хуже от него не станет. ;)

>> Программа должна что-то делать, хотя бы выводить "Hello world!".
Тогда это будет уже не минимальная программа. :D Но всё равно очень маленькая, если использовать не printf или cout << "...", а WriteConsole или WriteFile.

Естественно, все эти выкрутасы имеет смысл делать только в маленьких прогах. Попробуй-ка напиши большую прогу, используя только WinAPI. :) Но эато так писать легче, чем на асме, а результат получается ничуть не хуже (в 99.9% случаев).
3
19 сентября 2004 года
Green
4.8K / / 20.01.2000
Цитата:
Originally posted by Denri
Я же сказал 496. Работает нормально, но, действительно, ничего не делает. :)


В Windows для стандартного загрузчика минимальная граница выравнивания секций - 512 байт.
Сл-но, минимальная программа с одной единственной секцией будет занимать 1кб: вначале PE-заголовок, потом выравненная на 512 байт секция кода. Секция должна быть кратна 512 байтам, иначе загрузчик будет ругаться. Итого 512 + 512 = 1кб.

Покажи ка свою программу с параметрами компиляции и линковки, а так же в собранном виде.

Цитата:
Originally posted by Denri

Можно и без .h, если С++... Любая прога под винду его использует, да и хуже от него не станет. ;)


Любая ли?
Хуже не станет... ты всегда руководствуешься таким принципом при программировании?

Цитата:
Originally posted by Denri

>> Программа должна что-то делать, хотя бы выводить "Hello world!".
Тогда это будет уже не минимальная программа. :D


Да ну...
Ты считаешь, что вывод на экран одной строки займет более 512 байт?

Цитата:
Originally posted by Denri

Естественно, все эти выкрутасы имеет смысл делать только в маленьких прогах. Попробуй-ка напиши большую прогу, используя только WinAPI. :)


Ты считаешь, что основное наполнение программ - это обертка Win32 API?
Нет, это не так.

6.3K
20 сентября 2004 года
Denri
43 / / 12.08.2004
2 Green

Мы малость ушли от темы, но по теме тут и не говорят. :D
Поехали... Ладно, уберём нехороший windows.h

#------------- z.c ------------
unsigned __stdcall start(void){
return 0;
}
#------------------------------

MSC v13.10:
$ cl /Oxs z.c /link /entry:start /subsystem:windows /align:1

Получается работающий ехе-ник размером 467 байт.

Я не призываю всех писать и компилировать программы таким способом. Это всего лишь ради спортивного интереса...
3
20 сентября 2004 года
Green
4.8K / / 20.01.2000
Цитата:
Originally posted by Denri
$ cl /Oxs z.c /link /entry:start /subsystem:windows /align:1

Получается работающий ехе-ник размером 467 байт.



Хитрец... :D
В прошлом посте ты не указал /align:1.
Дело в том что этим параметром линковки ты принудительно определяешь границу выравнивания.

Ты перехитрил сам себя. Попробуй запустить свою "программу". Она не работает по причине того, что граница выравнивания, как я уже говорил, должна быть кратна 512.
В W9x выдается соответствующий диалог ошибки, а вот W2k просто ничего не выдает.
Т.к. твоя программа внешне ничего не делает, ты и не смог увидеть, что она НЕРАБОЧАЯ.
Но есть как минимум два способа проверить:
1) запустить под отладчиком и посмотреть как отвалится загрузчик;
2) посмотреть, какой код возвращает программа, например с помощью такого bat-файла:

 
Код:
z.exe
@echo %ERRORLEVEL%

По твоему исходнику, она должна возвращать 0, но возвращаемое значение иное ( 128 ).
6.3K
20 сентября 2004 года
Denri
43 / / 12.08.2004
Цитата:
Originally posted by Green


По твоему исходнику, она должна возвращать 0, но возвращаемое значение иное ( 128 ).



Не знаю, как на такую прогу смотрят старые винды, но NT 5.2 прекрасно переваривает и выдаёт ту цифру, что в исходнике написана. Под WinXP без вопросов работают более "серьёзные" проги, "выровненные" по 4 или 16. Если мне не изменяет склероз, одну такую прогу я успешно запускал под Win95.
Я согласен, что перед использованием подобных опций (особенно /merge) надо "семь раз отмерить", потому что иная прога может и не запуститься.
Неиспользование этих опций может увеличить итоговый размер на пару сотен байт, а использование библиотечных функций может добавить кило 50 веса...

3
20 сентября 2004 года
Green
4.8K / / 20.01.2000
Цитата:
Originally posted by Denri

Не знаю, как на такую прогу смотрят старые винды, но NT 5.2 прекрасно переваривает и выдаёт ту цифру, что в исходнике написана. Под WinXP без вопросов работают более "серьёзные" проги, "выровненные" по 4 или 16. Если мне не изменяет склероз, одну такую прогу я успешно запускал под Win95.



Ты полагаешься на свой склероз?
Надо бы опираться на факты, стандарты и документы.
Смотрим смотрим опцию линкера /ALIGN:

Цитата:

The number argument is in bytes and must be a power of two.


Надеюсь, теперь ясно, что /ALIGN:1 ошибочно?

Смотрим стандарт PE-format:

Цитата:

The value should be a power of 2 between 512 and 64K inclusive.



Смотрим описание структуры заголовка PE IMAGE_OPTIONAL_HEADER:

Цитата:

The value should be a power of 2 between 512 and 64K (inclusive).



Теперь делаем выводы:
1. Выравнивание дожно быть кратно 2, поэтому /align:1 не катит, не будет работать.
2. Выравнивание по стандарту должно быть не менее 512, поэтому /align:4, /align:16 работать под W9x не будет, а то, что работает под WinNT - не совсем соответствует стандарту и является исключением, а не правилом, сл-но нет никакой гарантии, что будет работать в последующих версиях, а так же с различными SP.

Цитата:
Originally posted by Denri

Я согласен, что перед использованием подобных опций (особенно /merge) надо "семь раз отмерить", потому что иная прога может и не запуститься.


А вот /megre относительно безопасен, главное, чтоб атрибуты доступа к секции соответствовали необходимым.

Цитата:
Originally posted by Denri

Неиспользование этих опций может увеличить итоговый размер на пару сотен байт, а использование библиотечных функций может добавить кило 50 веса...


Странно так образно говорить о библиотеках и так конкретно говорить о размере... :D

368
21 сентября 2004 года
rostyslav
629 / / 13.07.2004
Цитата:
Originally posted by Green


Ты полагаешься на свой склероз?
Надо бы опираться на факты, стандарты и документы.
Смотрим смотрим опцию линкера

[QUOTE]
The number argument is in bytes and must be a power of two.


Надеюсь, теперь ясно, что /ALIGN:1 ошибочно?[/QUOTE]
Green! исправь меня, если ошибаюсь, но 2 в степени 0 это не 1??:roll:

6.3K
21 сентября 2004 года
Denri
43 / / 12.08.2004
Цитата:
Originally posted by rostyslav
Green! исправь меня, если ошибаюсь, но 2 в степени 0 это не 1??:roll:


Вот именно.
Трудно доказать факт экспериментом, если он противоречит теории... В прошлом сообщении я приложил программу с выравниванием 16. Проверяйте. На WinNT 5.2 - безотказно.
Минимальная прога с не укладывающимся в понимание Green'а выравниванием 1 под той же ОС возвращает ровно то значение, которое укажешь. В данном случае, 0, но я проверял и другие.

2 Green
У меня в папочке лежат 9 программ. Если бы ты был прав, ни одна не запустилась бы. :)

3
21 сентября 2004 года
Green
4.8K / / 20.01.2000
Цитата:
Originally posted by rostyslav

Green! исправь меня, если ошибаюсь, но 2 в степени 0 это не 1??:roll:


Относительно степени ты прав.
Просто, /align:1 у меня везде не работает, поэтому для себя я трактовал это как 2^n, где n>0.

Цитата:
Originally posted by Denri

Вот именно.
Трудно доказать факт экспериментом, если он противоречит теории... В прошлом сообщении я приложил программу с выравниванием 16. Проверяйте. На WinNT 5.2 - безотказно.


Я ж сказал, что проверил. На W98 НЕ РАБОТАЕТ.
Почему не работает тоже объяснил.

Цитата:
Originally posted by Denri

Минимальная прога с не укладывающимся в понимание Green'а выравниванием 1 под той же ОС возвращает ровно то значение, которое укажешь. В данном случае, 0, но я проверял и другие.


Специально, для "Кулибиных", которым лень читать стандарты и полагающиеся лишь на "свой склероз", поставил эксперимент: на 4-х ОС из 5-ти не работает. Видимо, нужно показать в картинках, раз документы уже не котируются. Смотри прикрепленный файл с картинками.

Цитата:
Originally posted by Denri

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


Так у меня не работают, значит, я прав?
Или это локальная правда, в пределах одного компьютера? :D :D

Я уже столкнулся с твоими неординарным подходом к программированию:
1) "не помешает",
2) стандарты пишутся не для тебя.

А это, видимо, ещё один постулат: "у меня работает, значит все верно".
Непрофессионально, знаете ли...
Ты пользователям своих программных продуктов собираешься (не думаю, что ты уже с ними работаешь) так же объяснять причины неработоспособности твоих творений?

Кстати, ты так и не объяснил свою позицию, кроме как в анекдоте:
"Проверял? Тогда оставь как есть и ничего не трогай!"

Действительно, на все воля Божья, а пути его неисповедимы... :D

527
21 сентября 2004 года
pavor
275 / / 28.09.2003
Цитата:
Originally posted by rostyslav

Надеюсь, теперь ясно, что /ALIGN:1 ошибочно?


Green! исправь меня, если ошибаюсь, но 2 в степени 0 это не 1??:roll: [/QUOTE]
Я не знаю, в какой литературе хоть раз кто-то встречал, чтобы указывался размер, являющийся степенью двойки и допускалась степень 0? Давай тогда включим и -1, там ведь не написано?
/align:0.5
Даже блоки в памяти в Windows выровняны на слово.

368
21 сентября 2004 года
rostyslav
629 / / 13.07.2004
Цитата:
Originally posted by pavor

Я не знаю, в какой литературе хоть раз кто-то встречал, чтобы указывался размер, являющийся степенью двойки и допускалась степень 0? Давай тогда включим и -1, там ведь не написано?
/align:0.5
Даже блоки в памяти в Windows выровняны на слово.



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

и самое главное, я здесь невижу ответа на вопрос ProgMastera. Думаю, ему нужно бы использовать библиотеку ATL и ATL COM AppWizard.

368
21 сентября 2004 года
rostyslav
629 / / 13.07.2004
Цитата:
Originally posted by Green

Относительно степени ты прав.
Просто, /align:1 у меня везде не работает, поэтому для себя я трактовал это как 2^n, где n>0.


Мне кажется, что катимся в offtopic, но что поделаешь.

Есть директива #pragma pack(1), и теоретически он работает. Элементи последующих структур не выравниваются.

у Касперского: "Техника оптимизации программ" написано много о выравнивании. Если можно ему верить, то стат. и глоб. переменные выравниваются по усмотрению компилятора в соответствии с их размерами. pack или ALIGN не учитывается.

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

Динамические переменные, размещаются в куче. malloc напр. выравнивает выделяемые ей регионы по адресам, кратным 16.

3
21 сентября 2004 года
Green
4.8K / / 20.01.2000
Цитата:
Originally posted by rostyslav

и самое главное, я здесь невижу ответа на вопрос ProgMastera.



От части ты прав, надо бы ему ответить. :)
Но с другой стороны вопрос-ответ - это ближе к FAQ, чем к форуму.
Кроме того, ProgMastera некорректно задал вопрос.
Что значит "без использования АПИ"?
Без Win32 API? Без него не выйдет.
Без использования Win32 API напрямую, без врапперов? Тогда мой ответ - WTL/ATL.

Можно самому немного обернуть Win32 API и обойтись без WTL, MFC и т.п.
Я как-то для эксперимента использовал так Shell.Explorer через IWebBrowser2. Прога заняла пару кб. Если надо, могу покапаться в своем хламе.

3
21 сентября 2004 года
Green
4.8K / / 20.01.2000
Цитата:
Originally posted by rostyslav

Мне кажется, что катимся в offtopic, но что поделаешь.

Есть директива #pragma pack(1), и теоретически он работает. Элементи последующих структур не выравниваются.

у Касперского: "Техника оптимизации программ" написано много о выравнивании. Если можно ему верить, то стат. и глоб. переменные выравниваются по усмотрению компилятора в соответствии с их размерами. pack или ALIGN не учитывается.

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

Динамические переменные, размещаются в куче. malloc напр. выравнивает выделяемые ей регионы по адресам, кратным 16.



Ты путаешь выравнивание секций PE-файла и выравнивание полей структуры и данных.

Это разные вещи!

Если второе обусловлено компиляторами и критериями быстродействия, то первое обуславливается загрузчиком, точнее его реализацией и соответствию формату. При разработке PE-формата (точнее его предшественников) подразумевалось, что начало секции файла должно совпадать с началом сектора дефолтового размера на носителе. Почему, я уже не помню...

Что в описании PE-формата я уже приводил. Результаты работы загрузчиков различных ОС я тоже приводил.

6.3K
21 сентября 2004 года
Denri
43 / / 12.08.2004
Green, ты бы сначала понял, что именно я пытаюсь тебе доказать... Всё я проверил - Win9x требует выравнивать по 4096, а WinNT ничего не требует.
По 0.5, думаю, не стоит выравнивать. :D
ProgMaster не написал, что же именно он хочет запихать в 100 кб. А то, может, там такая мелочь, которая в 100 кб. без напряга сама уместится.
Вопрос о выравнивании данных относится к вопросам по ассемблеру. Ответ сильно зависит от структуры кеша процессора и памяти.
Не вижу смысла дальше обсуждать опцию компоновщика /align.
3
21 сентября 2004 года
Green
4.8K / / 20.01.2000
Цитата:
Originally posted by Denri
Green, ты бы сначала понял, что именно я пытаюсь тебе доказать...


Извини, так и не понял... Объясни, что же ты доказывал?
Разве не то, что программа собраная с опцией линкера /align:1 будет рабочей?

Цитата:
Originally posted by Denri

Вопрос о выравнивании данных относится к вопросам по ассемблеру. Ответ сильно зависит от структуры кеша процессора и памяти.
Не вижу смысла дальше обсуждать опцию компоновщика /align.


Мы же обсуждали выравнивание секций, а не данных...
Да и /align не имеет никакого отношения к выравниванию данных.
Или я опять в чем-то не разобрался в твоих постах? :D

Реклама на сайте | Обмен ссылками | Ссылки | Экспорт (RSS) | Контакты
Добавить статью | Добавить исходник | Добавить хостинг-провайдера | Добавить сайт в каталог