OberonCore

Библиотека  Wiki  Форум  BlackBox  Компоненты  Проекты
Текущее время: Четверг, 28 Март, 2024 22:46

Часовой пояс: UTC + 3 часа




Начать новую тему Ответить на тему  [ Сообщений: 9 ] 
Автор Сообщение
СообщениеДобавлено: Вторник, 31 Январь, 2023 16:01 

Зарегистрирован: Воскресенье, 25 Декабрь, 2022 23:14
Сообщения: 1163
предлагаю вот такое вот улучшение в LinKernel:

Код:
   PROCEDURE StrStartsWith (IN s, pfx: ARRAY OF CHAR): BOOLEAN;
   VAR
      pos: INTEGER;
   BEGIN
      pos := 0;
      WHILE (s[pos] # 0X) & (pfx[pos] # 0X) & (s[pos] = pfx[pos]) DO INC(pos) END;
      RETURN (pfx[pos] = 0X)
   END StrStartsWith;

   PROCEDURE StrStripDll (VAR s: ARRAY OF CHAR);
   VAR
      slen: INTEGER;
   BEGIN
      slen := LEN(s$);
      IF (slen > 4) & (s[slen - 4] = '.') &
         ((s[slen - 3] = 'd') OR (s[slen - 3] = 'D')) &
         ((s[slen - 2] = 'l') OR (s[slen - 2] = 'L')) &
         ((s[slen - 1] = 'l') OR (s[slen - 1] = 'L'))
      THEN
         s[slen - 4] := 0X
      END
   END StrStripDll;

   PROCEDURE StrHasSO (IN s: ARRAY OF CHAR): BOOLEAN;
   VAR
      pos, slen: INTEGER;
   BEGIN
      pos := 0; slen := LEN(s$);
      WHILE pos + 2 < slen DO
         WHILE (pos + 2 < slen) & ((s[pos] # '.') OR (s[pos + 1] # 's') OR (s[pos + 2] # 'o')) DO INC(pos) END;
         IF (s[pos] = '.') & (s[pos + 1] = 's') & (s[pos + 2] = 'o') &
            ((s[pos + 3] = 0X) OR (s[pos + 3] = '.')) THEN
            RETURN TRUE
         END;
         INC(pos, 3)
      END;
      RETURN FALSE
   END StrHasSO;

   PROCEDURE SStrPrepend (VAR s: ARRAY OF SHORTCHAR; IN pfx: ARRAY OF SHORTCHAR);
   VAR
      plen, slen, f: INTEGER;
   BEGIN
      plen := LEN(pfx$);
      IF plen > 0 THEN
         slen := LEN(s$);
         WHILE slen >= 0 DO s[slen + plen] := s[slen]; DEC(slen) END;
         FOR f := 0 TO plen - 1 DO s[f] := pfx[f] END
      END
   END SStrPrepend;

   (* k8: try "lib<dll>.so" first *)
   PROCEDURE TryDlOpen (IN dll: ARRAY OF CHAR): Dl.HANDLE;
   VAR
      soadded: BOOLEAN;
      res: INTEGER;
      h: Dl.HANDLE;
   BEGIN
      h := Dl.NULL;
      IF (LEN(dll) > 0) & (dll[0] # 0X) THEN
         (*log.String("***XXX***: dll=<"); log.String(dll); log.String(">"); log.Ln;*)
         tmpsonamebufL := dll$;
         StrStripDll(tmpsonamebufL);
         (*log.String("000: dll=<"); log.String(tmpsonamebufL); log.String(">"); log.Ln;*)
         (* append ".so" *)
         soadded := ~StrHasSO(tmpsonamebufL);
         IF soadded THEN tmpsonamebufL := tmpsonamebufL$ + ".so" END;
         (*log.String("001:   name=<"); log.String(tmpsonamebufL); log.String(">"); log.Ln;*)
         (* try with "lib" prefix *)
         IF ~StrStartsWith(tmpsonamebufL, "lib") THEN
            Utf.StringToUtf8(tmpsonamebufL, tmpsonamebuf, res); ASSERT(res = 0);
            SStrPrepend(tmpsonamebuf, "lib");
            (*log.String("002:   name=<"); log.String(LONG(tmpsonamebuf)); log.String(">"); log.Ln;*)
            h := Dl.dlopen(tmpsonamebuf, Dl.RTLD_LAZY + Dl.RTLD_GLOBAL);
         END;
         (* try without "lib" prefix *)
         IF h = Dl.NULL THEN
            (*log.String("003:   name=<"); log.String(tmpsonamebufL); log.String(">"); log.Ln;*)
            Utf.StringToUtf8(tmpsonamebufL, tmpsonamebuf, res); ASSERT(res = 0);
            h := Dl.dlopen(tmpsonamebuf, Dl.RTLD_LAZY + Dl.RTLD_GLOBAL);
         END;
         (* finally, try as is *)
         IF (h = Dl.NULL) & soadded THEN
            (*log.String("004:   name=<"); log.String(dll); log.String(">"); log.Ln;*)
            Utf.StringToUtf8(dll, tmpsonamebuf, res); ASSERT(res = 0);
            h := Dl.dlopen(tmpsonamebuf, Dl.RTLD_LAZY + Dl.RTLD_GLOBAL);
         END
      END;
      RETURN h
   END TryDlOpen;

   (* k8: FIXME: this completely wastes dll reference count! *)
   PROCEDURE (VAR p: Platform) LoadDll (IN name: ARRAY OF CHAR; VAR ok: BOOLEAN);
      (*VAR h: Dl.HANDLE; res: INTEGER; s: ARRAY Kernel.nameLen OF SHORTCHAR;*)
   BEGIN
      (*
      ok := FALSE;
      Utf.StringToUtf8(name, s, res); ASSERT(res = 0);
      h := Dl.dlopen(s, Dl.RTLD_LAZY +  Dl.RTLD_GLOBAL);
      IF h # Dl.NULL THEN ok := TRUE END
      *)
      ok := (TryDlOpen(name) # Dl.NULL)
   END LoadDll;

   PROCEDURE (VAR p: Platform) ThisDllObj (mode, _: INTEGER; IN dll, name: ARRAY OF CHAR): INTEGER;
      CONST mVar = 3; mProc = 4; (* sync with Kernel!! *)
      VAR ad: INTEGER; h: Dl.HANDLE; res: INTEGER; s: ARRAY Kernel.nameLen OF SHORTCHAR;
   BEGIN
      ad := 0;
      IF mode IN {mVar, mProc} THEN
         (*
         Utf.StringToUtf8(dll, s, res); ASSERT(res = 0);
         h := Dl.dlopen(s, Dl.RTLD_LAZY + Dl.RTLD_GLOBAL);
         *)
         h := TryDlOpen(dll);
         IF h # Dl.NULL THEN
            Utf.StringToUtf8(name, s, res); ASSERT(res = 0);
            ad := Dl.dlsym(h, s)
         END
      END;
      RETURN ad
   END ThisDllObj;


что делает: позволяет во многих случаях иметь один модуль импорта для win/lin. логика такая: отрезаем ".dll", если есть. если в конце нет ".so" — то добавляем. если в начале нет "lib" — то приставляем. пытаемся загрузить что получилось. если не вышло — пытаемся загрузить без приставленого "lib". если опять не вышло — пытаемся загрузить с оригинальным именем. в итоге имеем:
Код:
MODULE SQLiteLib ["sqlite3.dll"];

которое работает и в винде, и в линуксах.

в принципе, в виндокернел надо бы добавить нечто похожее, только наоборот. ;-) то есть, отрезать "lib" и ".so", если есть.

p.s.: а, да. ещё два глобала, чтобы в стек не гадить почём зря (всё равно у нас один поток):
Код:
      (* k8: temporary buffer for .so names; should be protected for MT when it will appear *)
      tmpsonamebuf: ARRAY 2048 OF SHORTCHAR;
      tmpsonamebufL: ARRAY 2048 OF CHAR;


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: BlackBox 2.0
СообщениеДобавлено: Четверг, 02 Февраль, 2023 18:20 
Аватара пользователя

Зарегистрирован: Четверг, 08 Октябрь, 2009 15:00
Сообщения: 3774
arisu писал(а):
предлагаю вот такое вот улучшение в LinKernel:

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


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: BlackBox 2.0
СообщениеДобавлено: Четверг, 02 Февраль, 2023 19:25 

Зарегистрирован: Воскресенье, 25 Декабрь, 2022 23:14
Сообщения: 1163
Иван Денисов писал(а):
arisu писал(а):
предлагаю вот такое вот улучшение в LinKernel:

Предложение очень полезное, особенно для вариантов, когда в линуксе в конце иногда там любят добавить какую-то цифру на разных дистрибутивах. Есть предложение перечислять варианты через запятую, чтобы было более явно.
цифры там по делу, это запрос конкретной версии библиотеки; если они есть, я их не трогаю. а если запрашивают «просто библиотеку», то загрузчик пытается её вот так найти.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: BlackBox 2.0
СообщениеДобавлено: Четверг, 02 Февраль, 2023 19:37 
Аватара пользователя

Зарегистрирован: Четверг, 08 Октябрь, 2009 15:00
Сообщения: 3774
arisu писал(а):
Иван Денисов писал(а):
arisu писал(а):
предлагаю вот такое вот улучшение в LinKernel:

Предложение очень полезное, особенно для вариантов, когда в линуксе в конце иногда там любят добавить какую-то цифру на разных дистрибутивах. Есть предложение перечислять варианты через запятую, чтобы было более явно.
цифры там по делу, это запрос конкретной версии библиотеки; если они есть, я их не трогаю. а если запрашивают «просто библиотеку», то загрузчик пытается её вот так найти.

Я о том, что это полумера. Так как одна и та же библиотека Sdl2 на разных платформах называется вот так
libSDL2-2.0.so.0
SDL2.DLL
А если полумера, то получается похоже на костыль. А если явно вот так писать?
MODULE Sdl2 ["SDL2.dll,libSDL2-2.0.so.0"];


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: BlackBox 2.0
СообщениеДобавлено: Четверг, 02 Февраль, 2023 19:39 

Зарегистрирован: Воскресенье, 25 Декабрь, 2022 23:14
Сообщения: 1163
Иван Денисов писал(а):
А если явно вот так писать?
MODULE Sdl2 ["SDL2.dll,libSDL2-2.0.so.0"];
а, понял. могу и так сделать, не проблема, просто не подумал. разве что в качестве разделителя, может, двоеточие взять? оно в именах файлов обычно не встречается, а запятая… мало ли… хотя в принципе, если кто-то в имени библиотеки поставил запятую, то он сумасшедший, нам такие не нужны. ;-)


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: Четверг, 02 Февраль, 2023 21:39 
Аватара пользователя

Зарегистрирован: Четверг, 08 Октябрь, 2009 15:00
Сообщения: 3774
Пусть это предложение полежит на форуме некоторое время, чтобы все желающие высказали за и против.


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: Четверг, 02 Февраль, 2023 21:52 

Зарегистрирован: Воскресенье, 25 Декабрь, 2022 23:14
Сообщения: 1163
в общем, переделал так: имена можно разделять пробелами, запятыми, двоеточиями и трубой. если в списке имён есть хотя бы одна библиотека с «.so» — загрузчик попробует её и сдаётся. если нет — то попробует вышеописаные замены.

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

а насчёт полежит… оно пусть лежит, а я в это время потестирую. если не будет возражений — то и закинем. а если будут — то решим в рабочем порядке.

p.s.: на всякий случай напоминаю, что это всё можно щупать в гите Lament Configuration. ;-)


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: Пятница, 03 Февраль, 2023 09:53 

Зарегистрирован: Воскресенье, 25 Декабрь, 2022 23:14
Сообщения: 1163
сделал такое же (с необходимыми изменениями) в WinKernel.


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: Пятница, 03 Февраль, 2023 10:11 

Зарегистрирован: Воскресенье, 25 Декабрь, 2022 23:14
Сообщения: 1163
кстати, такая реализация позволяет иметь несколько имён для динамической библиотеки: загрузчик будет их перебирать, пока они не кончатся, или пока что-то не найдётся. прикольный побочный эффект.


Вернуться к началу
 Профиль  
 
Показать сообщения за:  Поле сортировки  
Начать новую тему Ответить на тему  [ Сообщений: 9 ] 

Часовой пояс: UTC + 3 часа


Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 8


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

Найти:
cron
Вся информация, размещаемая участниками на конференции (тексты сообщений, вложения и пр.) © 2005-2024, участники конференции «OberonCore», если специально не оговорено иное.
Администрация не несет ответственности за мнения, стиль и достоверность высказываний участников, равно как и за безопасность материалов, предоставляемых участниками во вложениях.
Без разрешения участников и ссылки на конференцию «OberonCore» любое воспроизведение и/или копирование высказываний полностью и/или по частям запрещено.
Powered by phpBB® Forum Software © phpBB Group
Русская поддержка phpBB