Подтвердить что ты не робот

Кто такая диана, и почему она не сможет скомпилировать мои объекты базы данных?

ОК, поэтому заголовок вопроса немного застенчив, но вопрос достаточно серьезный. Иногда, компилируя объекты в схеме или импортируя файл дампа, я вижу следующее сообщение об ошибке:

ORA-04028: cannot generate diana for object SCOTT.VW_EMP

что это значит, и как я могу его избежать?

4b9b3361

Ответ 1

Релевантно здесь: PL/SQL, размер пакета, узлы дерева анализа, строки кода.

Диана - это язык определения интерфейса Oracles для представления структуры таблиц базы данных и логики модулей программы PL/SQL в качестве атрибутов деревьев.

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

Поэтому проверьте размер логики PL/SQL и строки кода. Возможно, это невозможно или даже необходимо знать фактические пределы, которыми может управлять ваша версия.

Как только вы узнаете, где правильный размер вашего пакета, половина проблемы решена.

Сообщите нам, когда вы решили другую половину, спасибо.

Ответ 2

Можете ли вы поделиться своим фрагментом кода, в котором вы получаете сообщение об ошибке.

Вот описание, которое может помочь вам понять, почему вы получаете ошибку: PL/SQL основан на языке программирования ADA. поэтому, когда вы пишете pgram в PL/SQL, он генерирует "DIANA" → описательную промежуточную атрибутированную нотацию для Ada, древовидного промежуточного языка. DIANA используется внутри компиляторами и другими инструментами.

Как это работает: 1) Во время компиляции исходный код PL/SQL преобразуется в системный код и генерирует соответствующий DIANA.

2) Оба DIANA и системный код для подпрограммы или пакета хранятся в базе данных.

3) Во время выполнения они загружаются в пул разделяемой памяти.

4) DIANA используется для компиляции зависимых подпрограмм; более конкретно, чтобы проверить/подтвердить, что подпрограмма все еще действительна. это необходимо, потому что, поскольку мы знаем, что подпрограмма может использовать объекты базы данных, такие как таблицы, представления, синонимы или другие хранимые процедуры. возможно, что объекты могут быть изменены/удалены/удалены при следующем запуске программы. Например: кто-то мог бы отбросить таблицу, может быть изменена сохраненная функция proc или функции.

5) Как только проверка выполняется с помощью DIANA, системный код просто запускается.

Ограничение вашей программы:

В пуле разделяемой памяти спецификация пакета, спецификация ADT, автономная подпрограмма или анонимный блок ограничены 67108864 (2 ** 26) узлами DIANA, которые соответствуют токенам, таким как идентификаторы, ключевые слова, операторы и т.д. Это позволяет использовать ~ 6 000 000 строк кода, если вы не превысите лимиты, налагаемые компилятором PL/SQL

вы можете сослаться на эту ссылку: http://docs.oracle.com/cd/E14072_01/appdev.112/e10472/limits.htm#

Теперь приступим к вашей проблеме - ora-04028:

Это может быть вызвано одной из следующих причин:

1) Есть некоторые ошибки, которые дают эту ошибку при выборе из представления, в котором вызывается функция, которая также выбирает из одного и того же представления

2) Каталог сервера базы данных, клиента или rman не находится в соответствующей версии. Вам нужно будет запланировать

3) Вы пытаетесь зарегистрировать экземпляр Oracle 11g в каталоге RMAN 10.2.0.1. Чтобы это удалось, обновите каталог до версии 10.2.0.3

Ответ 3

По Документация Oracle,

PL/SQL основан на языке программирования Ada. PL/SQL использует вариант описательной промежуточной атрибутивной нотации для Ada (DIANA), древовидного промежуточного языка. Он определяется с помощью мета-нотации, называемой языком определения интерфейса (IDL). DIANA используется внутри компиляторами и другими инструментами.

Во время компиляции исходный код PL/SQL преобразуется в машиночитаемый m-код. Оба DIANA и m-код для процедуры или пакета хранятся в базе данных. Во время выполнения они загружаются в пул разделяемой памяти. DIANA используется для компиляции зависимых процедур; m-код просто выполняется.

К сожалению, вы не можете оценить количество узлов DIANA из разбора размера. Для двух программных модулей с одинаковым разборным размером могут потребоваться 1500 и 2000 узлов DIANA, соответственно, потому что, например, второй блок содержит более сложные SQL-инструкции.

Спросить тома

Подробнее о расчетах DIANA node, прочитайте эту книгу "Ада-Европа" 93: 12-я Международная конференция "Ада-Европа", Париж, Франция, 14-18 июня 1993 года. Труды "

Следующая заметка поддержки хорошо освещает этот вопрос...

Article-ID:         <Note:62603.1>
Folder:             PLSQL
Topic:              General Information Articles
Title:              'PLS-123 Program too Large' - Size Limitations on PLSQL 
                    Packages
Document-Type:      BULLETIN
Impact:             MEDIUM
Skill-Level:        NOVICE
Server-Version:     07 to 08
Updated-Date:       13-JUN-2000 17:41:01
References:         

Обзор

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

PLS-123 Program too large

Ограничения по размеру пакетов PL/SQL

В выпусках до 8.1.3 большие программы привели к ошибке PLS-123. Это произошло из-за неподдельных ограничений в компиляторе; а не в результате ошибки.

При компиляции блока PL/SQL компилятор строит дерево разбора. Максимальный размер Единица PL/SQL определяется размером дерева разбора. Максимальное число узлов дианы существует в этом дереве.

До 7,3, вы могли бы иметь 2 * * 14 (16K) узлов дианы и от 8.0 до 8.1.3, 2 * * 15 (32K) были разрешены узлы дианы. В 8.1.3 этот предел был ослаблен, так что теперь вы можете имеют 2 * * 26 (т.е. 64M) узлы дианы в этом дереве для тел пакета и типа.

Ограничения исходного кода

Хотя нет простого способа перевести ограничения в терминах строк исходного кода, мы наблюдали, что в строке исходного кода было приблизительно 5-10 узлов. До 8.1.3 компилятор мог скомпилировать до 3000 строк кода.

Начиная с 8.1.3, предел был ослаблен для корпусов корпусов и типов тел, которые теперь могут иметь приблизительно до 6 000 000 строк кода.

Примечания. Этот новый предел применяется только к телам пакетов и типам тел. Кроме того, вы можете начать использовать некоторые другие ограничения для компилятора, прежде чем вы нажмете этот лимит компилятора.

В терминах размера исходного кода предположим, что токены (идентификаторы, операторы, функции и т.д.) имеют в среднем четыре символа. Тогда максимальным будет:

   Up to 7.3:         4 * (2 * * 14)=64K
   From 8.0 to 8.1.3: 4 * (2 * * 15)=128K
   With 8.1.3:        4 * (2 * * 25)=256M

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

Обратите внимание, что это для каждого модуля программы, поэтому тела пакета, скорее всего, столкнутся с этим предел.

Как проверить текущий размер пакета

Чтобы проверить размер пакета, ближайший номер, который вы можете использовать, - PARSED_SIZE в словарь словаря данных USER_OBJECT_SIZE. Это значение обеспечивает размер DIANA в байтов, хранящихся в таблицах SYS.IDL_xxx $, и НЕ является размером в общем пуле.

Размер части DIANA кода PL/SQL (используемой во время компиляции) намного больше в общий пул, чем в системной таблице.

Например, вы можете начать испытывать проблемы с ограничением 64K, когда PARSED_SIZE в USER_OBJECT_SIZE не более 50K.

Для пакета анализируемый размер или размер DIANA имеет смысл только для целого объект, а не отдельно для спецификации и тела.

Если вы выберете parsed_size для пакета, вы получите отдельный размер источника и кода для спецификации и тела, но только значимый проанализированный размер для всего объекта, который выводится на линии для спецификации пакета. Для параметра parsed_size выводится 0 на линии для корпуса упаковки.

В следующем примере показано это поведение:

CREATE OR REPLACE PACKAGE example AS  
  PROCEDURE dummy1;  
END example;  
/  
CREATE OR REPLACE PACKAGE BODY example AS  
  PROCEDURE dummy1 IS  
  BEGIN  
    NULL;  
  END;  
END;  
/  

SQL> start t1.sql;  

Package created.  


Package body created.  

SQL> select parsed_size from user_object_size where name='EXAMPLE';  


PARSED_SIZE  
-----------  
        185  
          0  


SQL> select * from user_object_size where name='EXAMPLE';  

  .....

Oracle хранит как DIANA, так и MCODE в базе данных. MCODE - это фактический код, который запускается, в то время как DIANA для конкретного библиотечного блока X содержит информацию, которая необходима для компилировать процедуры, используя библиотечную единицу X.

Ниже приведены несколько примечаний:

a) DIANA представлена ​​в IDL. Линейная версия IDL хранится на диске. фактическое дерево разбора создается и сохраняется в общем пуле. Вот почему размер DIANA в общем пуле обычно больше, чем на диске.

b) DIANA для вызываемых процедур требуется в общем пуле только при создании процедуры. В производственных системах нет необходимости в DIANA в общем пуле (но только для MCODE).

c) Начиная с выпуска 7.2, DIANA для корпусов упаковки выбрасывается, не используется, и не сохраняется в базе данных. Вот почему PARSED_SIZE (т.е. Размер DIANA) УПАКОВКИ - 0.

Поэтому необходимо всегда определять большие процедуры и функции в пакетах!

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

Ответ 4

В Oracle 10.2.5 обнаружена ошибка (Unpublished Bug 9342254, см. Doc ID 1505092.1), для которой существует исправление Oracle 11.1 и новее; Я думаю, что это могло быть проблемой здесь.

Вы можете обойти его, выпустив флеш общего пула:

ALTER SYSTEM FLUSH SHARED_POOL

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

Ответ 5

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

alter session set plsql_debug=false; 

или для всей базы данных:

alter system set plsql_debug=false;