Добро пожаловать в форум, Guest  >>   Войти | Регистрация | Поиск | Правила | В избранное | Подписаться
Все форумы / Oracle Новый топик    Ответить
 внешняя библиотека на Си  [new]
relav
Member

Откуда:
Сообщений: 204
Вычислительная задача была внесена во внешнюю функцию написанную на Си, для ускорения вычислений. При тестировании
данной функции на Си время оказалось следующим: при первом запуске функции - 20 секунд, а при следующих запусках -0.6 секунд. Я объясняю такую разность показателей времени тем, что оракл при первом запуске функции загружает библиотеку в память, на что тратится время, а при последующих вызовах функции библиотека уже в памяти и следовательно загружать ее не нужно, что отражается на времени. Меня интересует, верно ли я объясняю разницу времени и если верно, то как можно библиотеку раз загрузить и чтоб оракл ее оставил в памяти и не выгружал?
21 июн 16, 12:51    [19318420]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
-2-
Member

Откуда:
Сообщений: 15330
relav,

Внешние процедуры запускаются листенером как отдельный процесс. Prespawn настраивается в листенере.
Но 20-0.6 секунд на запуск процесса это перебор. Причина в другом.
21 июн 16, 13:09    [19318523]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
dbms_photoshop
Member

Откуда: sqlmdx.net
Сообщений: 5151
relav
Я объясняю такую разность
Ну я надеюсь ты проанализировал что значит каждая из букв DDL и как выполняется связывание конкретно в Оракле через extproc.
relav
можно библиотеку раз загрузить и чтоб оракл ее оставил в памяти и не выгружал?
Нельзя. Отдельный экземпляр для каждой сессии.
21 июн 16, 13:11    [19318533]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
dbms_photoshop
Member

Откуда: sqlmdx.net
Сообщений: 5151
dbms_photoshop
каждая из букв DLL
Мдэээ...
21 июн 16, 13:12    [19318542]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
dbms_photoshop
Member

Откуда: sqlmdx.net
Сообщений: 5151
relav,

Сколько занимает первый и последующий вызовы при линковке к своему бинарнику а не к Ораклу?
21 июн 16, 13:17    [19318570]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
andrey_anonymous
Member

Откуда: Москва
Сообщений: 18399
Если вычисления подразумевают выделение заметного объема памяти (особенно мелкими порциями), то дело может быть в этом.
21 июн 16, 13:22    [19318598]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
relav
Member

Откуда:
Сообщений: 204
dbms_photoshop,

не понимаю, что имеется ввиду?
21 июн 16, 13:22    [19318600]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
andrey_anonymous
Member

Откуда: Москва
Сообщений: 18399
relav
dbms_photoshop,
не понимаю, что имеется ввиду?

С очевидностью имеется ввиду чистый эксперимент - выполнение вычислений данной библиотекой без привлечения oracle.
Напишите программку (скорее всего уже написана - ведь тестировали как-то), которая выполнит ровно те же вычисления, что и при вызове через oracle
21 июн 16, 13:25    [19318614]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
Leonid Kudryavtsev
Member

Откуда:
Сообщений: 9278
Вряд ли под "вычислениями" подразумевается что-то безумное сложное над 2-мя числами на 20 сек.. А вот дальше вопрос, что дергает автор из этой библиотеки.

Если C-код дергает Oracle-левые ф-ции, то причина может быть банальная: SGA, buffer cache и так далее )))

От замены PL/SQL на C производительность может повысится, а может и понизиться. Сама по себе латинская буква "c" в название языка программирования прирост производительности НЕ гарантирует )))
21 июн 16, 13:31    [19318656]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
relav
Member

Откуда:
Сообщений: 204
Leonid Kudryavtsev,

а с этим не может быть связана задержка?

After the external procedure completes, the agent remains active throughout your Oracle Database session; when you log off, the agent is killed. Consequently, you incur the cost of launching the agent only once, no matter how many calls you make. Still, you should call an external procedure only when the computational benefits outweigh the cost.
21 июн 16, 14:20    [19318924]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
Leonid Kudryavtsev
Member

Откуда:
Сообщений: 9278
Да с чем угодно может быть связана задержка.

Не очень понятно, какую задачу/проблему решаете. В зависимости от задачи - нужно выбирать средство.

Подход "на С быстро, на PL/SQL медленно" очень детский. Так же как и подход "при первом запуске функции - 20 секунд, а при следующих запусках -0.6 секунд. Я объясняю..."

Родные средства Oracle: SQL (Select), PL/SQL, в какой-то мере Java... внешние: C и прочее.

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

-2-
Внешние процедуры запускаются листенером как отдельный процесс. Prespawn настраивается в листенере.
Но 20-0.6 секунд на запуск процесса это перебор. Причина в другом.

Плюсуюсь.

Возможно у автора сами вычисления быстрые, а при первом вызове выполняется какая-то долгая инициализация данных. Но это все равно проблема алгоритма/программиста, а не Oracle.
21 июн 16, 14:44    [19319041]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
orawish
Member

Откуда: Гадюкино-2 (City)
Сообщений: 15487
Leonid Kudryavtsev
Да с чем угодно может быть связана задержка.

Не очень понятно, какую задачу/проблему решаете. В зависимости от задачи - нужно выбирать средство.

Подход "на С быстро, на PL/SQL медленно" очень детский. Так же как и подход "при первом запуске функции - 20 секунд, а при следующих запусках -0.6 секунд. Я объясняю..."

Родные средства Oracle: SQL (Select), PL/SQL, в какой-то мере Java... внешние: C и прочее.

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

-2-
Внешние процедуры запускаются листенером как отдельный процесс. Prespawn настраивается в листенере.
Но 20-0.6 секунд на запуск процесса это перебор. Причина в другом.

Плюсуюсь.

Возможно у автора сами вычисления быстрые, а при первом вызове выполняется какая-то долгая инициализация данных. Но это все равно проблема алгоритма/программиста, а не Oracle.

+1
я бы назвал - "святая" истина предпоследнего десятилетия прошлого века
2 ТС
с той поры столько "более других" вариантов явилось и пере-появилось (и это потому, что оно таки болело )
короче, имхо, хотите си - пишите на си, но не забывайте сравнить решение с pl/sql + (например) реалнативкомпиляцией
21 июн 16, 16:23    [19319528]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
Вячеслав Любомудров
Member

Откуда: Владивосток
Сообщений: 18487
-2-
relav,

Внешние процедуры запускаются листенером как отдельный процесс. Prespawn настраивается в листенере.
Но 20-0.6 секунд на запуск процесса это перебор. Причина в другом.
Про какой Prespawn идет речь?

Может, имеется ввиду Multithreaded extproc Agent?
22 июн 16, 03:12    [19321278]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
Cristiano_Rivaldo
Member

Откуда:
Сообщений: 346
В коде библиотеки есть функция malloc ?
23 июн 16, 15:49    [19326835]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
relav
Member

Откуда:
Сообщений: 204
Cristiano_Rivaldo,

в коде есть функции OCIMemoryAlloc().

Я делал замер времени в си коде с помощью функции clock и результат оказался удивительным. Время выполнения си программы занимает 5 секунд, а когда вызываешь программу из оракла, оракл отрабатывает 20 секунд, куда девается 15 секунд - не понятно.
Код pl/sql привожу:
+
 FUNCTION f_getOffsettedQuality(locationId integer, locationType integer) RETURN quality_tab
  IS
      l_quality_level quality_tab := quality_tab();
      l_level varchar2(10) := 0;
      lMinx float;
      lMaxX float;
      lMinY float;
      lMaxY float;
      cnt integer;
      lcity_id integer;
      locBlob BLOB;
      gsmOffset integer := 100; --default value for location offsetting
      umtsOffset integer := 100; --default value for location offsetting
      OffsetX    Number ; 
      OffsetY    Number ;       
      l_offset1 Binary_Integer := 0;
      l_offset2 Binary_Integer := 0;
      l_area    Double precision:=0.0;
      l_proc    Double Precision :=0.0;  
      cover binary_integer;      
      c varchar2(100);
  BEGIN
       IF locationType = 0 THEN--house
            
           Select hg.gis_xmin, hg.gis_xmax, hg.gis_ymin, hg.gis_ymax, s.city 
             into lMinx, lMaxX, lMinY, lMaxY,lcity_id 
           from house_gis hg 
           Join house h On hg.id = h.id
           Join street s On h.street = s.id
           where hg.id = locationId;
           --check if exists config for city_id and get offsetting
           select count(*) 
             into cnt 
           from DICT.CITY_CONFIG cc 
           where cc.city_id = lcity_id;
           
           if cnt > 0 then 
               select nvl(cc.sig_house_gsm, gsmOffset), nvl(cc.sig_house_3g, umtsOffset) 
                 into gsmOffset, umtsOffset 
               From CITY_CONFIG cc 
               where cc.city_id = lcity_id;
           else  
               select nvl(cc.sig_house_gsm, gsmOffset), nvl(cc.sig_house_3g, umtsOffset) 
                 into gsmOffset, umtsOffset 
               From CITY_CONFIG cc 
               where cc.city_id = 0;
           end if;
           
           select h.gis into locBlob from house_gis h where h.id = locationId;
                     
       ELSIF locationType = 1 THEN--street
           select distinct h.gis_xmin, h.gis_xmax, h.gis_ymin, h.gis_ymax, s.city 
             into lMinx, lMaxX, lMinY, lMaxY, lcity_id 
           from street_gis h, street s 
           where s.id = h.id and h.id = locationId;
           --check if exists config for city_id and get offsetting
           select count(*) 
              into cnt 
           from DICT.CITY_CONFIG cc 
           where cc.city_id = lcity_id;
           
           if cnt > 0 then 
               select nvl(cc.sig_house_gsm, gsmOffset), nvl(cc.sig_house_3g, umtsOffset) 
                  into gsmOffset, umtsOffset 
               from CITY_CONFIG cc 
               where cc.city_id = lcity_id;
           else  
               select nvl(cc.sig_house_gsm, gsmOffset), nvl(cc.sig_house_3g, umtsOffset) 
                 into gsmOffset, umtsOffset 
               from CITY_CONFIG cc 
               where cc.city_id = 0;
           end if;
           
           select h.gis 
             into locBlob 
           from street_gis h 
           where h.id = locationId;
                  
       ELSIF locationType = 2 THEN--city
           select distinct h.gis_xmin, h.gis_xmax, h.gis_ymin, h.gis_ymax, h.id 
             into lMinx, lMaxX, lMinY, lMaxY,lcity_id 
           from city_gis h 
           Join city c On h.id = c.id
           where h.id = locationId;
           --check if exists config for city_id and get offsetting
           select count(*) into cnt 
           from DICT.CITY_CONFIG cc 
           where cc.city_id = lcity_id;
           
           if cnt > 0 then 
               select nvl(cc.sig_house_gsm, gsmOffset), nvl(cc.sig_house_3g, umtsOffset) 
                 into gsmOffset, umtsOffset 
               from CITY_CONFIG cc 
               where cc.city_id = lcity_id;
           end if;
           
           select h.gis 
             into locBlob 
           from city_gis h 
           where h.id = locationId;
                      
       END IF;

       OffsetX := gsmOffset;
       OffsetY := gsmOffset;
       pac_geocoding.p_meters2geo(OffsetX, OffsetY);
          
       FOR r IN 
       (
           SELECT g1.gis, g1.threshold,g1.gis_xmax,g1.gis_xmin,g1.gis_ymax,g1.gis_ymin
           FROM coverage.QUALITY_GIS g1
           WHERE g1.signal_type = 'GSM' AND g1.detail_m = 5
               AND (lMinx - OffsetX < g1.gis_xmax 
               AND lMaxX + OffsetX > g1.gis_xmin 
               AND lMinY - (OffsetY ) < g1.gis_ymax 
               AND lMaxY + (OffsetY ) > g1.gis_ymin) --offsetted bounds..don't ask...
           ORDER BY g1.threshold  DESC       
       )          
       Loop
-- call external c function
              pac_gis.PolygonsIntersection(r.gis,locBlob,r.gis_xmax,r.gis_xmin,r.gis_ymax,r.gis_ymin,cover);

              $IF pac_3g_service.debugging=1 $THEN    
                dbms_output.put_line('threshold ='||r.threshold||' area='||l_area);
              $END            
              
           IF cover = 1  THEN
              l_level := r.threshold;
              EXIT;
           END IF;
       
       END LOOP;
              
       IF l_level != 0 THEN
         l_quality_level.extend();  
         cnt := l_quality_level.count;
         l_quality_level(cnt) := quality_t('',''); 
         l_quality_level(cnt).Standart := 'GSM';  
         l_quality_level(cnt).Sig_Level:= l_level;
         l_level := 0;
         cover   := 0;
       END IF;
      -- ==================================== 
       OffsetX := umtsOffset;
       OffsetY := umtsOffset;
       pac_geocoding.p_meters2geo(OffsetX, OffsetY);
                  
       FOR r IN 
       (
           SELECT g1.id,g1.gis, g1.threshold,g1.gis_xmax,g1.gis_xmin,g1.gis_ymax,g1.gis_ymin
           FROM coverage.QUALITY_GIS g1
           WHERE g1.signal_type = 'UMTS' AND g1.detail_m = 5
               AND (lMinx - OffsetX < g1.gis_xmax 
               AND lMaxX + OffsetX > g1.gis_xmin 
               AND lMinY - (OffsetY ) < g1.gis_ymax 
               AND lMaxY + (OffsetY ) > g1.gis_ymin) --offsetted bounds..don't ask...
           ORDER BY g1.threshold  DESC       
       )          
       Loop
--call external c function        
             pac_gis.PolygonsIntersection(r.gis,locBlob,r.gis_xmax,r.gis_xmin,r.gis_ymax,r.gis_ymin,cover);
             
              $IF pac_3g_service.debugging=1 $THEN    
                dbms_output.put_line('threshold ='||r.threshold||' area='||l_area);
              $END 

           IF cover = 1  THEN
             l_level := r.threshold;
             EXIT;
           END IF;
 
       END LOOP;               
       
       IF l_level != 0 THEN
         l_quality_level.extend();  
         cnt := l_quality_level.count;
         l_quality_level(cnt) := quality_t('','');  
         l_quality_level(cnt).Standart := '3G';  
         l_quality_level(cnt).Sig_Level:= l_level;    
       END IF;
       $IF pac_3g_service.debugging=1 $THEN 
           dbms_output.put_line('f_getQuality rc='||l_quality_level.count);
           FOR r IN 1..l_quality_level.count LOOP
               dbms_output.put_line('standart='||l_quality_level(r).standart||' level='||l_quality_level(r).sig_level);
           END LOOP;
       $END 

       RETURN l_quality_level;
  END;
28 июн 16, 17:31    [19346852]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
dbms_photoshop
Member

Откуда: sqlmdx.net
Сообщений: 5151
relav,

Для определения узкого места имеет сравнивать один вызов при линковке к сишному бинарнику и один вызов при линковке к Ораклу как тебя уже было сказано. Зачем ты запостил сюда 200 строчек говнокода совершенно непонятно.
Если проблема определить где узкое место в pl/sql - используй dbms_trace/dbms_hprof, но по твоему первому посту проблема определить куда уходит время при первом вызове сишной библиотеки.
Неужели подход по выкидыванию не нужного
28 июн 16, 17:46    [19346925]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
dbms_photoshop
Member

Откуда: sqlmdx.net
Сообщений: 5151
dbms_photoshop
relav,

Для определения узкого места имеет смысл сравнивать один вызов при линковке к сишному бинарнику и один вызов при линковке к Ораклу как тебя уже было сказано. Зачем ты запостил сюда 200 строчек говнокода совершенно непонятно.
Если проблема определить где узкое место в pl/sql - используй dbms_trace/dbms_hprof, но по твоему первому посту проблема определить куда уходит время при первом вызове сишной библиотеки.
Неужели подход по выкидыванию ненужного так сложен для понимания.
Fixed.
28 июн 16, 17:47    [19346936]     Ответить | Цитировать Сообщить модератору
 Re: внешняя библиотека на Си  [new]
Jonhson
Member

Откуда: Мск
Сообщений: 979
dbms_photoshop как всегда сама доброта
28 июн 16, 18:53    [19347204]     Ответить | Цитировать Сообщить модератору
Все форумы / Oracle Ответить