Особенности нарезки Python довольно обширны.
синтаксис выглядит так: SOME_STRING[start:stop:step]
.
Таким образом, в основном вы можете использовать его в значительной степени, как вам нравится.
Я хотел бы прокомментировать это в вашем комментарии, но, к сожалению, мне не хватает rep:)
В данном случае не безопасно назвать fclose () снова, поскольку в стандарте C говорится, что поток разъединен из файла (и становится неопределенным), даже если вызов перестал работать.
Я не думаю, что существует простой способ на самом деле протестировать это по желанию.
EINTR будет сгенерирован, если fclose операция будет прервана сигналом. Это подразумевает, что fclose был в фоновом потоке, который получил сигнал, поскольку он обрабатывал близкий запрос.
Удача, пытающаяся воспроизвести то стечение обстоятельств.
Используйте структуру указателей функции к краткому обзору системные функции. Замените вызов к flcose (fp) с чем-то как sys-> fclose (fp). В Вашем модульном тесте создайте реализацию fclose, который всегда возвращается, EINTR затем устанавливают sys-> fclose к той версии.
Смотря на исходный код ядра Linux, я не могу найти любые драйверы, которые даже возвращают EINTR на файл близко.
Если Вы, absosmurfly должен был воспроизвести этот случай, Вы могли бы записать свой собственный драйвер в Linux для возврата-EINTR на .release методе. Смотрите на пример кода из книги Драйверов устройств Linux O'Reilly. Проект весла является одним из самых простых. Вы изменили бы его, чтобы быть похожими на это:
int scull_release(struct inode *inode, struct file *filp)
{
return -EINTR;
}
Снова, хотя, держа через исходное дерево Linux, я не могу найти драйвер, который возвратил бы EINTR на завершении.
РЕДАКТИРОВАНИЕ - хорошо это похоже на предохранитель - файловая система пространства пользователя смогла. Это используется для вещей как sshfs. Все еще пограничный случай все же.
Как Крис предполагает, временно замените вызовы к "реальному" fclose()
с Вашей собственной реализацией, определенной в Вашем коде модульного теста. Ваша реализация могла сделать что-то столь же простое как:
int my_fclose(FILE *fp)
{
errno = EINTR;
return EOF;
}
Но, как вызов в суд указывает, Вы не должны звонить fclose()
снова, поскольку поведение не определено, таким образом, Вы не должны потрудиться даже проверять на условие.
Другой вопрос спросить состоит в том, необходимо ли действительно волноваться об этом; если Ваш код приложения должен был заблокировать все возможные сигналы (кроме SIGKILL и SIGSTOP) во время Вашего fclose()
затем Вы не получили бы EINTR и не должны будете волноваться вообще.
Вот то, как я протестировал бы его, только ради тестирования, так как вызов в суд напомнил нам вызов fclose()
дважды небезопасно.
Возможно переопределить fclose()
(или любая другая функция libc) в Вашей программе с Вашим собственным поведением. В подобных Unix системах компоновщик не жалуется - никогда не примерял Windows, но с cygwin. Конечно, это предотвращает Ваши другие тесты для использования реального fclose()
, поэтому такой тест должен быть помещен в отдельный тестовый исполняемый файл.
Вот единый пример с minunit.
#include <errno.h>
#include <stdio.h>
#include <stdbool.h>
/* from minunit.h : http://www.jera.com/techinfo/jtns/jtn002.html */
#define mu_assert(message, test) do { if (!(test)) return message; } while (0)
#define mu_run_test(test) do { char *message = test(); tests_run++; \
if (message) return message; } while (0)
int tests_run = 0;
bool fclose_shall_fail_on_EINTR = false;
//--- our implemention of fclose()
int fclose(FILE *fp) {
if (fclose_shall_fail_on_EINTR) {
errno = EINTR;
fclose_shall_fail_on_EINTR = false; //--- reset for next call
return EOF;
} else { return 0; }
}
//--- this is the "production" function to be tested
void uninterruptible_close(FILE *fp) {
// Given an open FILE *fp
while (fclose(fp)==EOF && errno==EINTR) {
errno = 0;
}
}
char *test_non_interrupted_fclose(void) {
FILE *theHandle = NULL; //--- don't care here
uninterruptible_close(theHandle);
mu_assert("test fclose wo/ interruption", 0 == errno);
return 0;
}
char *test_interrupted_fclose(void) {
FILE *theHandle = NULL; //--- don't care here
fclose_shall_fail_on_EINTR = true;
uninterruptible_close(theHandle);
mu_assert("test fclose wo/ interruption", 0 == errno);
return 0;
}
char *test_suite(void)
{
mu_run_test(test_non_interrupted_fclose);
mu_run_test(test_interrupted_fclose);
return 0;
}
int main(int ac, char **av)
{
char *result = test_suite();
printf("number of tests run: %d\n", tests_run);
if (result) { printf("FAIL: %s\n", result); }
return 0 != result;
}
Хм, я думаю, все вы игнорируют кое-что очень важное.
fclose () не может вернуть EINTR. Не могут ни fopen (), fwrite (), fread (), ни какие-либо стандартные функции CI / O.
Это только тогда, когда вы балуетесь низкоуровневыми вызовами ввода-вывода, такими как open (2), write ( 2) и выберите (2), который вам нужен для обработки EINTR.
Прочтите [смешные] страницы руководства