Важная информация

User Tag List

Страница 3 из 10 ПерваяПервая 1234567 ... ПоследняяПоследняя
Показано с 21 по 30 из 99

Тема: "Умная линковка" в компиляторах

  1. #21
    Member
    Регистрация
    21.05.2006
    Адрес
    Canada
    Сообщений
    78
    Спасибо Благодарностей отдано 
    3
    Спасибо Благодарностей получено 
    2
    Поблагодарили
    2 сообщений
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Совет, кажется, слияние сообщения, так что я не могу получить комнату, чтобы поставить русских в, извините: (

    = english ==


    Цитата Сообщение от Oleg N. Cher Посмотреть сообщение
    So I think:

    Many functions = One module = One source file (.h and .c) => One library

    And you think:

    One function = One module = One source file
    Many functions = Many modules = Many source files => One library
    It actually comes down to how the language itself works.

    One source file per function is exactly what is required by assembly language and C (no surprise as C was meant to model assembly language programming) and the incremental linking method invented in the 1960s is exactly sufficient for "smart linking" C and asm programs.

    A C program not destined for a library would organize related functions on a per file basis and in user programs, it's ok to have more than one function per file because presumably the user only writes functions he uses. When it comes time to make a library, it's not a big deal to take all the functions from one file and separate them into one file per function in a directory by hand. The directory acts like the class or module name, the functions in the directory are clearly visible to anyone looking for what they can do with the library and the incremental linking makes sure only what is needed is attached to the binary. The code is organized and easier to use as it's easier to see what is available.

    BUT, this only works because asm and C have just two scopes -- local and global. With imperative languages like Pascal and object oriented languages, there is more than one scope. Taking Pascal as an example, a single module (? it's been a long time since I've programmed in pascal) can have many nested functions and variables in different scopes. The functions in such a module cannot be simply separated by hand into individual files for the linker -- you have to modify names to enforce scoping rules. Object oriented languages require something similar that is not easily done by hand. "Smart linking" solves this problem by automatically extracting individual functions from these nested scopes or files and breaking them into units that works for the incremental linker.

    I need to have Pascal/Oberon point of view to this problem.
    So I agree with you here, you need this for Pascal-like languages and oo languages. Modern day linkers still work in an incremental fashion and "smart linking" is something done by the compiler. A C compiler (like sdcc) will never need such functionality so your adding it to the toolchain as a separate utility is the right thing to do. Placing it at the C source level is a good way to do it too, and may be an occasionally useful tool for C programmers. It's how modern day compilers do it (or it was at one time), although they may not show you all the hundreds of individual files they generate and instead directly generate a library file.

    Q-Master's alternative of generating a define to opt in and out of parts of the source code is another way to go that does not run into scoping issues (below). However, it only works at the source level. If you wanted to write a library in Pascal using this method and export it for use by C programmers or asm programmers, you couldn't without also exporting the source of this library in Pascal and the build environment. That's not what you want.

    The difficulty with "smart linking" is it changes the scope of functions and variables. By extracting each individual function into its own file, you make that function global.

    Problems in C:

    static int a = 5;

    static int multiply(int a, int b)
    {
    return a*b;
    }

    main()
    {
    return multiply(a,6);
    }

    If you extract that multiply() function, you're adding it to the global scope but the C code is specifically making it local. You could end up with more than one function with name "multiply" and the linker may either complain or incorrectly link the first one it finds. You've also got the issue of how you are going to properly scope the local variable "a" above.

    In Pascal-derived languages the problems are even worse because you can have many nested scopes.

    Usually this is solved with judicious use of name-mangling. Above, the local variable "a" would be renamed to "xyz_a" and the local function "multiply" would be similarly renamed to "xyz_multiply". The references in main to these things would also be changed. "xyz" is some identifier that uniquely identifies the translation unit those functions are found in but it cannot be something totally random as, when building a library, you want those names to be predictable if it is to be accessed by another program or the symbols are to be understood while debugging.

    Doing this requires the "smart linker" to have a lot of knowledge of the language it is splitting up and it's not a trivial program to write. So although Q-Master's method is less desirable, it does avoid these scoping problems.

    I prefer your method but I don't think you have solved the scoping issues? Maybe that's what everyone is talking about when they mention clang, etc. The automatic translation is not always easy to follow.

    ---------- Post added at 10:33 ---------- Previous post was at 09:52 ----------

    Цитата Сообщение от Valen Посмотреть сообщение
    Да,я я так и делал изначально, у себя в sdcc framework.
    Пример (либа для вызова FLOS функций из Си кода)
    http://sourceforge.net/p/v6z80p/code...terface_for_c/[COLOR="Silver"]
    Yes, that is the right way to do things for C libraries and adding a "FLOS" scope to functions helps to prevent name clashes

    For functions implemented in asm, I'd suggest a slightly different approach from what I have seen here that separates the asm implementation from the C interface.

    Separating the asm implementation has a couple of advantages:

    1. You can easily accommodate different C linkages. Right now sdcc only has one linkage but it's not a good one for interfacing asm code and sometime down the road there will be alternative linkages. In z88dk we have many different linkages: sdcc R->L param order, small C L->R param order, fastcall, callee. We also have two different sdcc C interfaces: one for the library using ix and one for the library using iy. The latter leads to smaller code because the library does not have to preserve the value of ix. All of these C interfaces use the same asm implementation without any overhead.

    2. Your library code becomes attractive to asm programmers. The first thing many asm programmers do when they look at C libraries is turn up their noses because of the bulky C interface code. sdcc's C interface is very bulky and this discourages asm programmers from using library code. In z88dk we completely separate the asm implementation from the C interface so that is possible to build an asm library without any C overhead.

    3. The C libraries have entry points for both C code and asm code. This allows easy mingling of C and asm in programs.

    The last thing I would change from some of the code I've seen is to stop using ix to index parameters passed to an asm function. It's very slow and leads to large code. It is almost always better to pop passed parameters into registers before proceeding with the asm implementation.


    An example of what I suggest, using an asm implementation of strcpy():

    File: asm_strcpy.asm

    Код:
    PUBLIC asm_strcpy
    
    asm_strcpy:
       
       ; enter : hl = char *s2 = src
       ;         de = char *s1 = dst
       ;
       ; exit  : hl = char *s1 = dst
       ;         de = ptr to terminating NUL in s1
       ;
       ; uses  : af, bc, de, hl
    
       push de
       xor a
    
    loop:
    
       cp (hl)
       ldi
       jr nz, loop
       
       pop hl
       dec de
       ret
    The sdcc C interface:

    File: strcpy.asm
    Код:
    ; char *strcpy(char * restrict s1, const char * restrict s2)
    
    PUBLIC _strcpy
    
    _strcpy:
    
       pop af
       pop de
       pop hl
       
       push hl
       push de
       push af
       
       INCLUDE "string/z80/asm_strcpy.asm"
    The z88dk C interface using callee linkage, just to show that the same asm code is being used:

    File: strcpy_callee.asm
    Код:
    ; char *strcpy(char * restrict s1, const char * restrict s2)
    
    PUBLIC strcpy_callee
    
    strcpy_callee:
    
       pop af
       pop hl
       pop de
       push af
       
       INCLUDE "string/z80/asm_strcpy.asm"
    The header file for the compiler:

    FILE: string.h
    Код:
    extern char *strcpy(void *dst, void *src);
    The INCLUDEs mean there is no JP or CALL overhead to the asm implementation. The same labels from the asm implementation are available so that the C interface version also has the asm interface.

    Several versions of the library are built: one for asm programmers where the asm implementation is used, one for the sdcc library where the sdcc C interface is used, etc.

    Notice that none of it is embedded into a C wrapper -- this is unnecessary when a function is implemented in asm. You scan skip the compiler entirely and use the assembler directly to make the library. Using a C wrapper is not entirely harmless as sometimes preamble and postamble code may be inserted by the compiler.
    Последний раз редактировалось Alcoholics Anonymous; 11.06.2014 в 22:36.

  2. #22
    Veteran Аватар для Oleg N. Cher
    Регистрация
    24.08.2007
    Адрес
    Днепропетровская обл.
    Сообщений
    1,598
    Спасибо Благодарностей отдано 
    2,182
    Спасибо Благодарностей получено 
    137
    Поблагодарили
    103 сообщений
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Господа, что в сухом остатке.

    • Споры о точности формулировок являются неконструктивными. Обсуждение не-спектрумных средств разработки является оффтопиком. Вместо этого:
    • Нужно пролоббировать обсуждаемую нами "умную линковку" в сообщество разработчиков SDCC и tcc. Тогда вопрос об использовании smartlib станет неактуальным как минимум в контексте разработки на SDCC.
    • Надо разработать и адаптировать на SDCC побольше библиотек для ZX.


    Цитата Сообщение от Alcoholics Anonymous Посмотреть сообщение
    I prefer your method but I don't think you have solved the scoping issues?
    Ofront (and later, me) use name-mangling by such way:
    Код:
    MODULE Abc;
    IMPORT Fast, Compact, Standard, MyOwn; (* Different libraries *)
    
    CONST A=5; (* internal constant *)
    B* = 10; (* external/exported constant. the C-name is Abc_B *)
    
    PROCEDURE GetCompactMult* (): INTEGER; (* C name is Abc_GetCompactMult *)
    BEGIN
      RETURN Compact.Mult(A, B); (* Used compact-way *)
    END GetMult;
    
    PROCEDURE GetFastMult* (): INTEGER; (* C name is Abc_GetFastMult *)
    BEGIN
      RETURN Fast.Mult(A, B); (* Used fast-way *)
    END GetFastMult;
    
    END Abc. (* No conflict of names *)
    All the name conflict problems were solved by Josef Templ, the author of Ofront translator.

    Цитата Сообщение от Alcoholics Anonymous Посмотреть сообщение
    Maybe that's what everyone is talking about when they mention clang, etc. The automatic translation is not always easy to follow.
    You prefer C/asm coding. I prefer to code in Oberon and translate to C. Ofront is my assistant of this work - it translates Oberon to C automatically. And yes, C is closer to the low-level coding, and more suitable for coding for Z80 than Oberon - I know.
    Последний раз редактировалось Shadow Maker; 17.06.2014 в 20:18.

  3. #23
    Vitamin C++ Аватар для Vitamin
    Регистрация
    14.01.2005
    Адрес
    Таганрог, Россия
    Сообщений
    4,255
    Спасибо Благодарностей отдано 
    9
    Спасибо Благодарностей получено 
    83
    Поблагодарили
    35 сообщений
    Mentioned
    7 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Oleg N. Cher, технический вопрос по поводу твоей утилиты разрезания на функции.
    Как обрабатываются приватные (static) функции?

  4. #24
    Veteran Аватар для Oleg N. Cher
    Регистрация
    24.08.2007
    Адрес
    Днепропетровская обл.
    Сообщений
    1,598
    Спасибо Благодарностей отдано 
    2,182
    Спасибо Благодарностей получено 
    137
    Поблагодарили
    103 сообщений
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Vitamin, сама утилита ничего особо умного не делает, но делает буквально следующее. Берёт сишный файл-исходник библиотеки со множеством функций:
    Код:
    #include "SYSTEM.h"
    
    export void NewSupercode_EKRAN_1 (SHORTCARD x);
    export void NewSupercode_EKRAN_2 (SHORTCARD x);
    /*================================== Header ==================================*/
    
    void NewSupercode_EKRAN_1 (SHORTCARD x) {
    __asm
        LD   HL, #2
        ADD  HL, SP
        LD   L, (HL) // x
        LD   H, #0
        LD   DE, #0x5800
        LD   BC, #0x300
        LDIR
    __endasm;
    } //NewSupercode_EKRAN_1
    
    /*--------------------------------- Cut here ---------------------------------*/
    void NewSupercode_EKRAN_2 (SHORTCARD x) {
    __asm
        LD   HL, #2
        ADD  HL, SP
        LD   L, (HL) // x
        LD   H, #0
        LD   BC, #0x1800
        LD   DE, #0x4000
        LDIR
    __endasm;
    } //NewSupercode_EKRAN_2
    
    ...
    и нарезает на секции по "линиям разреза", так что получаются фрагменты, состоящие из заголовка, взятого до "линии заголовка" - он будет включен в каждый фрагмент (притом какие-либо инклюды из заголовка делать вовсе необязательно, ибо даже можно сделать нужный инклюд прямо в нужном куске). Фрагмент NewSupercode_001:
    Код:
    #include "SYSTEM.h"
    
    export void NewSupercode_EKRAN_1 (SHORTCARD x);
    export void NewSupercode_EKRAN_2 (SHORTCARD x);
    /*================================== Header ==================================*/
    
    void NewSupercode_EKRAN_1 (SHORTCARD x) {
    __asm
        LD   HL, #2
        ADD  HL, SP
        LD   L, (HL) // x
        LD   H, #0
        LD   DE, #0x5800
        LD   BC, #0x300
        LDIR
    __endasm;
    } //NewSupercode_EKRAN_1
    Фрагмент NewSupercode_002:
    Код:
    #include "SYSTEM.h"
    
    export void NewSupercode_EKRAN_1 (SHORTCARD x);
    export void NewSupercode_EKRAN_2 (SHORTCARD x);
    /*================================== Header ==================================*/
    
    void NewSupercode_EKRAN_2 (SHORTCARD x) {
    __asm
        LD   HL, #2
        ADD  HL, SP
        LD   L, (HL) // x
        LD   H, #0
        LD   BC, #0x1800
        LD   DE, #0x4000
        LDIR
    __endasm;
    } //NewSupercode_EKRAN_2
    Потом эти кусочки в цикле скармливаются компилятору и библиотекарю, который упаковывает скомпилированные сегменты-объектники .rel в библиотеку.

    Сам понимаешь, что приватные (static) функции при таком способе разбиения имеет смысл пихать только в тот фрагмент, который монопольно будет вызывать приватную функцию, потому что если выделить static-функцию в отдельный фрагмент - её извне не будет видно. Хотя никто и не запрещает.

    Также я научил Ofront добавлять в генерируемый им сишный исходник те же линии заголовка и разреза, но решены отнюдь не все проблемы с автоматическим разделением, поэтому его можно использовать только в простых случаях (без static и без ООП), но поймите меня правильно: это излечимо, просто нужно придумать как доработать. Подчёркиваю: последний абзац касается только Ofront'а, которым вы всё равно не пользуетесь (и не собираетесь). Поэтому я дорабатываю его исключительно для себя. С SDCC же весь процесс регулируется ручками, так больше свободы.

  5. #25
    Vitamin C++ Аватар для Vitamin
    Регистрация
    14.01.2005
    Адрес
    Таганрог, Россия
    Сообщений
    4,255
    Спасибо Благодарностей отдано 
    9
    Спасибо Благодарностей получено 
    83
    Поблагодарили
    35 сообщений
    Mentioned
    7 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Цитата Сообщение от Oleg N. Cher Посмотреть сообщение
    Сам понимаешь, что приватные (static) функции при таком способе разбиения имеет смысл пихать только в тот фрагмент, который монопольно будет вызывать приватную функцию, потому что если выделить static-функцию в отдельный фрагмент - её извне не будет видно. Хотя никто и не запрещает.
    В том и прикол, что эти приватные функции, зачастую, нужны более чем одной функции. А значит придется либо выставлять наружу то, что там не нужно, либо потерять в оптимизации (дублировать эту приватную функцию у всех пользователей, либо резать не по функциям, а по группам функций.
    Плюс необходимость ручной работы по разметке- не фонтан (я думал, там более продвинутая автоматика)...
    В общем, разработчику компилятора еще есть над чем работать. Как минимум, можно предоставлять информацию о связанности функций для автоматизации нарезки.

  6. #26
    Master
    Регистрация
    26.03.2005
    Адрес
    Ivanovo
    Сообщений
    640
    Спасибо Благодарностей отдано 
    5
    Спасибо Благодарностей получено 
    3
    Поблагодарили
    1 сообщение
    Mentioned
    2 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Цитата Сообщение от Oleg N. Cher Посмотреть сообщение
    Ну вот. Вы предложили "разрезание без разрезания", фактически то же самое, что и я, только более сложным способом. И потом, зачем мне вражеская libtool вместо моей крохотной smartlib, к которой Ofront я уже адаптировал.
    Специально повторяюсь, поскольку заметил что Вы просто НЕ ЧИТАЕТЕ то что я пишу. Я сказал КАК в libtool, но не сказал что надо использовать libtool.
    И мой (точнее стандартный) способ лишен тех проблем про которые говорит Витамин.
    Более того, такой способ полностью убирает необходимость чего-либо куда-либо резать и компиляция происходит значительно оптимальнее. Если есть желание, то я могу написать утилиту, которая Вашу нарезку переводит в #ifdef #endif.

    Цитата Сообщение от Oleg N. Cher Посмотреть сообщение
    Видите ли, в чём ещё проблема, Q-Master. Я компиляю сишные исходники, сгенерированные автоматически Ofront'ом. Поэтому вариант допихивать в них потом ручками #ifdef'ы выглядит абсолютно искусственно. Но это ещё полбеды, у варианта с libtool хватает и других недостатков.
    Думаю что доработать Ofront проблем вообще никаких нет.

    Цитата Сообщение от Oleg N. Cher Посмотреть сообщение
    Кстати, обероновский подход не одобряет огромные модули, наоборот, поощряются мелкие. Так что ваши попытки приписать мне идею запихивания всего-чего-можно в один мегаисходник тоже идут мимо. Истина как всегда где-то посередине.
    Тогда я не понимаю проблемы с линковкой вообще. Ее просто нет. Более того, изначальный вопрос о вариантах после Ваших-же слов становится как-то бессмысленен. Если Вас все устраивает и Вы полностью отвергаете все предложения, то какой смысл был вообще что-то спрашивать?

    PS: Я за свою жизнь понаписал столько всего и на стольких языках, что говорю, обычно, не "для галочки".

  7. #27
    Veteran Аватар для Oleg N. Cher
    Регистрация
    24.08.2007
    Адрес
    Днепропетровская обл.
    Сообщений
    1,598
    Спасибо Благодарностей отдано 
    2,182
    Спасибо Благодарностей получено 
    137
    Поблагодарили
    103 сообщений
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Цитата Сообщение от Vitamin Посмотреть сообщение
    В том и прикол, что эти приватные функции, зачастую, нужны более чем одной функции. А значит придется либо выставлять наружу то, что там не нужно, либо потерять в оптимизации
    Я за выставление её наружу, заманглировав предварительно имя таким образом, чтобы не было возможности вызвать её из Оберона (а для Си - снабдить её префиксом "__"). Ну и в Оберон-интерфейсе она мелькать не будет.

    Цитата Сообщение от Vitamin Посмотреть сообщение
    Плюс необходимость ручной работы по разметке- не фонтан (я думал, там более продвинутая автоматика)...
    Я не против автоматизации и доработки утилиты, мне не нравится критика тех, кому это не нужно и кто не собирается ничего дорабатывать, лишь учит нас жизни с умудрённым видом.

    Цитата Сообщение от Vitamin Посмотреть сообщение
    В общем, разработчику компилятора еще есть над чем работать. Как минимум, можно предоставлять информацию о связанности функций для автоматизации нарезки.
    Если сделать всё внутри SDCC, то никакой информации не будет нужно. Фрагменты нарезания будут самые атомарные. Браться будут по требованию. Лишнего не будет взято.

    Цитата Сообщение от Q-Master Посмотреть сообщение
    И мой (точнее стандартный) способ лишен тех проблем про которые говорит Витамин.
    А в чём преимущество прогонять целый исходник столько раз, сколько там функций? Вы ведь никак не решаете проблему инклюдов, только предлагаете засорять исходник #ifdef'ами, усложняя его и портя стиль разработки. И как вы предлагаете решать проблему локальных (static) функций, про которую говорит Витамин?

    Цитата Сообщение от Q-Master Посмотреть сообщение
    Более того, такой способ полностью убирает необходимость чего-либо куда-либо резать и компиляция происходит значительно оптимальнее.
    Т.е. прогон исходника в 100 кб, скажем, 100 раз вы называете более оптимальным, чем прогон 100 раз однокилобайтных кусочков нарезки? Мдя, по-моему у нас разговор ушёл вообще какие-то абстрактные области, не подхлёстываемый ничем, кроме пипискомера. Мне жаль это констатировать. Я не вижу преимущества в предлагаемом вами способе. Более того, переход на него в моём случае связан ещё и с накладными расходами по переходу. Смысл?

    Цитата Сообщение от Q-Master Посмотреть сообщение
    Думаю что доработать Ofront проблем вообще никаких нет.
    Нет. Вот поговорить об этом - проблем никаких нет. А доработать - это вообще мало кому под силу. А я нахожу там массу нерешённых проблем, поэтому делаю пошагово после того как полностью понята стадия следующего шага. Сейчас автоматизации разбивки можно подвергать не-ООП библиотеки без локальных функций. Дальше буду двигаться по мере необходимости.

    Я вообще сейчас знаете как делаю? Транслирую Ofront'ом, но всю Си-библиотеку веду ручками и ручками в неё переношу оттранслированные куски. Пока объёмы работы небольшие - такой вариант приемлем.

    Цитата Сообщение от Q-Master Посмотреть сообщение
    Тогда я не понимаю проблемы с линковкой вообще. Ее просто нет. Более того, изначальный вопрос о вариантах после Ваших-же слов становится как-то бессмысленен.
    Ну как это проблемы просто нет? Ещё как есть проблема. Об этом прочитайте постами выше. Проблема в SDCC, который пихает весь исходник библиотеки без возможности смартлинковки, одним сегментом. Приходится делать библиотеку в виде кучи маленьких файлов. Вот проблема. Это не проблема только для тех, кто делает всё кусочками и вводит это в ранг религии. Но есть противоположная религия цельности.

    И конечно решать данную проблему никто в здравом уме в этой теме не пойдёт, зачем, вдруг юродивый Oleg N. Cher когда-нить этим займётся, а мы подождём, куда нам спешить, и потом попользуемся плодами. Ведь давить инакомыслящих - гораздо более интересное занятие.

    Цитата Сообщение от Vitamin Посмотреть сообщение
    В том и прикол, что эти приватные функции, зачастую, нужны более чем одной функции.
    Vitamin, а как решить проблему двух зайцев: a) и чтобы static функция сидела в библиотеке отдельным куском; b) и чтобы вызывать её из других функций по её имени; c) и чтобы её нельзя было вызывать из некоторых более других функций по её имени, т.е. чтобы наружу это имя не светилось.

    Мне нравится сама постановка задачи! Но средствами XDev (Oberon-Ofront-smartlib) она решаема автоматическим манглированием Си-имён. Т.е. из модуля Abc, написанного на Си, вызываются нелокальные конечно, но все функции модуля Abc. А вот из Оберон-модуля Cde нельзя вызвать static-функции модуля Abc, которые не экспортированы в интерфейс модуля.

    Цитата Сообщение от Vitamin Посмотреть сообщение
    Как минимум, можно предоставлять информацию о связанности функций для автоматизации нарезки.
    Я думаю, после приведённого мною примера NewSupercode уже понятно как можно решать эту задачу средствами smartlib.
    Последний раз редактировалось Shadow Maker; 17.06.2014 в 20:22.

  8. #28
    Activist Аватар для Sergey
    Регистрация
    23.12.2006
    Адрес
    Славный город Самара
    Сообщений
    473
    Спасибо Благодарностей отдано 
    94
    Спасибо Благодарностей получено 
    12
    Поблагодарили
    8 сообщений
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Цитата Сообщение от Sergey Посмотреть сообщение
    У асма, кстати, есть такая функция объявлять неизвестные имена глобальными. И этот ключик ему можно передать из sdcc.
    Код:
    sdcc -mz80 -c -Wa -g filename.c
    После этого, вроде как, не обязательно каждой функции хедер давать. Все либы так собираю, - вроде, полёт нормальный.
    К сожалению, оказался не прав: фокус не сработает, если в функциях используются "самодельные" типы данных, которые без хедера компилятор не распознает и выдаст ошибку синтаксиса. Не сталкивался с этим, потому что меня умиляет писать типы полностью, например, "unsigned char", а не заменять на свои типа "u8".
    С уважением,
    Gris / Red Triangle.
    _____________________________________
    ZX-EVO/TS-Labs config/NGS/HDD/SD-card
    Amiga A1200/Blizzard 1230@50/32/60GB
    Amiga A1200/Apollo 1260@66/32/60GB
    UnAmiga (C5) AGA GM7123 VideoDAC

  9. #29
    Master
    Регистрация
    26.03.2005
    Адрес
    Ivanovo
    Сообщений
    640
    Спасибо Благодарностей отдано 
    5
    Спасибо Благодарностей получено 
    3
    Поблагодарили
    1 сообщение
    Mentioned
    2 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Цитата Сообщение от Oleg N. Cher Посмотреть сообщение
    А в чём преимущество прогонять целый исходник столько раз, сколько там функций? Вы ведь никак не решаете проблему инклюдов, только предлагаете засорять исходник #ifdef'ами, усложняя его и портя стиль разработки. И как вы предлагаете решать проблему локальных (static) функций, про которую говорит Витамин?
    Для тех кто очень крут, но не знает что есть компиляция в С и пре-процессор я скажу. Прогон будет не 100 раз, а ровно 1 раз на 1 инклюд хедера и 1 раз при компиляции самого файла, что есть быстрее чем компиляция 100 файлов примерно в 100 раз. Выполняться будет препроцессором компилятора в памяти и происходить мегабыстро без создания кучи временных файлов, которые потом будет проблематично пере-использовать, т.к. имена генерируются автоматически и расчитывать на них нельзя. Заголовочный файл в данном случае будет 1(2-3-10 неважно) и так-же при пре-процессинге из него будет выкидываться все ненужное.
    Проблема, которую описал Витамин решается автоматически в виду исключения какой-либо резьбы по дереву и объявления ф-ций там где надо. Более того такие статические ф-ции могут быть обернуты в комплексные ifdef'ы и подключаться ТОЛЬКО в случае надобности, что опять-же очень ускорит компиляцию.

    Цитата Сообщение от Oleg N. Cher Посмотреть сообщение
    Т.е. прогон исходника в 100 кб, скажем, 100 раз вы называете более оптимальным, чем прогон 100 раз однокилобайтных кусочков нарезки? Мдя, по-моему у нас разговор ушёл вообще какие-то абстрактные области, не подхлёстываемый ничем, кроме пипискомера. Мне жаль это констатировать. Я не вижу преимущества в предлагаемом вами способе. Более того, переход на него в моём случае связан ещё и с накладными расходами по переходу. Смысл?
    В твоем (задолбало писать Вашем) случае 100 кб кусок кода будет по моему методу прогнан 1 раз ровно и скомпилирован в 1 .о файл который будет 1 раз прилинкован к собираемому приложению. По твоему методу это будет:
    прогон 100кб файла нарезателем и сохранение 100 кусков по килобайту (в реальности с учетом хэдеров и статических ф-ций будет не по килобайту, а по полтора-два). Потом 100 компиляций в 100 объектных файлов и 100 линковок. Соотвтетственно в случае ошибки в моем случае 1 компиляция, в твоем от 1 до 100.
    Преимущество очевидно и не требует переноса (в случае смены компилятора или платформы для компиляции) утилиты по нарезке и лечения ее багов буде такие найдутся.

    Цитата Сообщение от Oleg N. Cher Посмотреть сообщение
    Ну как это проблемы просто нет? Ещё как есть проблема. Об этом прочитайте постами выше. Проблема в SDCC, который пихает весь исходник библиотеки без возможности смартлинковки, одним сегментом. Приходится делать библиотеку в виде кучи маленьких файлов. Вот проблема. Это не проблема только для тех, кто делает всё кусочками и вводит это в ранг религии. Но есть противоположная религия цельности.
    Я уже сказал что это не проблема sdcc, а проблема исключительно придуманная и тщательно лелеемая. Пре-процессор полностью решает ее без использования сторонних утилит.

    ---------- Post added at 15:48 ---------- Previous post was at 15:47 ----------

    Цитата Сообщение от Sergey Посмотреть сообщение
    Таки нужна. Может для других Си-систем, нет, а д
    Таки не нужна, если пользоваться ВСЕМИ возможностями компиляторов С.

  10. #30
    Veteran
    Регистрация
    26.11.2013
    Адрес
    г. Новосибирск
    Сообщений
    1,042
    Спасибо Благодарностей отдано 
    934
    Спасибо Благодарностей получено 
    227
    Поблагодарили
    122 сообщений
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Цитата Сообщение от Q-Master Посмотреть сообщение
    по моему методу прогнан 1 раз ровно и скомпилирован в 1 .о файл который будет 1 раз прилинкован к собираемому приложению.
    Я правильно понимаю, что это будет каждый раз, при сборке приложения, которое использует библиотеку?


    Цитата Сообщение от Q-Master Посмотреть сообщение
    прогон 100кб файла нарезателем и сохранение 100 кусков по килобайту (в реальности с учетом хэдеров и статических ф-ций будет не по килобайту, а по полтора-два). Потом 100 компиляций в 100 объектных файлов
    А это только при компиляции библиотеки? То есть при использовании библиотеки, происходит 100 линковок и только.

    ---------- Post added at 18:10 ---------- Previous post was at 18:03 ----------

    Если да, то получается у Q-Master велосипед с квадратными колёсами, у Oleg N. Cher с треугольными. А правильный велосипед, это нормальный линковщик, который режет умно объектные файлы.

Страница 3 из 10 ПерваяПервая 1234567 ... ПоследняяПоследняя

Информация о теме

Пользователи, просматривающие эту тему

Эту тему просматривают: 1 (пользователей: 0 , гостей: 1)

Похожие темы

  1. Ответов: 17
    Последнее: 26.12.2015, 23:22
  2. Ответов: 19
    Последнее: 30.09.2011, 03:08
  3. Ответов: 0
    Последнее: 15.08.2010, 14:38
  4. Ответов: 18
    Последнее: 27.08.2008, 20:27
  5. Ответов: 6
    Последнее: 20.11.2007, 11:29

Ваши права

  • Вы не можете создавать новые темы
  • Вы не можете отвечать в темах
  • Вы не можете прикреплять вложения
  • Вы не можете редактировать свои сообщения
  •