#c #oracle #fork #oracle-pro-c
Вопрос:
Вкратце…
int main() { pid_t childPid; EXEC SQL CONNECT :username IDENTIFIED BY :password; for (;;) { childPid = fork(); if(childPid gt; 0) { // parent process ... ... ... } else if(childPid == 0) { // chiled process EXEC SQL DECLARE c1 CURSOR FOR SELECT empno, ename, sal FROM emp; for (;;) { EXEC SQL OPEN c1; EXEC SQL FETCH c1 INTO :emp_rec; if(sqlca.sqlcode == 1403) { EXEC SQL CLOSE c1; EXEC SQL COMMIT WORK RELEASE; break; } ... ... //A function that sends results to the Client program. SendPacketTOClient(fd,size); } EXEC SQL COMMIT WORK; exit(0); } else { // fork Fail perror("fork Fail! n"); return -1; } sleep(60); } retun 0; }
Как и выше, ПОДКЛЮЧЕНИЕ к БД выполняется в родительском процессе, и вилки выполняются каждую минуту, а дочерний процесс завершается выходом (0) после запроса (ОБЪЯВИТЬ-gt;ОТКРЫТЬ-gt;gt;ВЫБОРКА-gt;gt;gt;ЗАКРЫТЬ). Не было никаких проблем, потому что он был обработан до ПОЛУЧЕНИЯ. Но если ЗАКРЫТЬ не работает должным образом, позже произошла ошибка ORA-01000: максимальный открытый ответ. Когда я на самом деле проверил, дочерний процесс был создан, и он не закрылся, когда был завершен после завершения работы.
После Serch я обнаружил, что это была проблема, потому что процесс Servie был одним, поэтому я решил ее, разветвив родительский процесс и подключение к БД дочернего процесса.
Я решил эту проблему, но я хочу знать принцип, поэтому я оставляю вопрос. Могу я узнать, почему выполняются ОБЪЯВЛЕНИЯ, ОТКРЫТИЯ и ВЫБОРКИ, но COLSE не выполняется?
Спасибо.
Комментарии:
1. Из опубликованного вами кода (в котором есть ошибка, как будто(sqlca.sqlcode==1403 не закрыт), вы извлекаете только одну строку из курсора, а затем проверяете, дошли ли вы до конца, чтобы закрыть ее, затем открываете ее снова и извлекаете. Таким образом, если ваш курсор возвращает строки, вы не закрываете его до следующего открытия, и в итоге у вас будет много открытых курсоров. И поскольку все ваши разветвленные процессы используют одно и то же соединение, поэтому все открываемые ими курсоры вносят вклад в один и тот же максимум, вы доберетесь туда очень быстро.
2. @gsalen Спасибо вам за ваш ответ. Как вы сказали, ошибка была исправлена. И я еще не решил эту проблему. Для выживания дочернего процесса требуется менее 10 секунд. Время сна родительского процесса составляет 1 минуту. Таким образом, перед ОТКРЫТИЕМ КУРСОРА следующего дочернего процесса выполняется ВЫБОРКА и дочерний процесс завершается. В этом случае значение sqlcode после ЗАКРЫТИЯ КУРСОРА равно 0 (нормально), тем не менее, мне интересно, почему курсор не закрывается.
3. Попробуйте распечатать sqlcode после выборки и посмотрите, что вы получите. Вероятно, бот 1403.