Справочник функций

Ваш аккаунт

Войти через: 
Забыли пароль?
Регистрация
Информацию о новых материалах можно получать и без регистрации:

Почтовая рассылка

Подписчиков: -1
Последний выпуск: 19.06.2015

Синхронизация потоков

67K
02 апреля 2011 года
Егор Ворожцов
10 / / 02.04.2011
В процессе есть основной поток, который читает из текстового файла, и есть второй поток, который записывает данные в тот же файл. Как можно проиллюстрировать присутствие/отсутствие синхронизации потоков? Записываемые данные абсолютно произвольные, метод - критические секции.
278
02 апреля 2011 года
Alexander92
1.1K / / 04.08.2008
Заставьте каждый поток ждать, к примеру, 2 секунды перед выходом. Тогда, если синхронизация работает правильно, то временной интервал между любыми изменениями вашего файла будет >= 2 секунды.
67K
02 апреля 2011 года
Егор Ворожцов
10 / / 02.04.2011
очень интересная идея. наверное, как-раз подойдет, спасибо!
67K
03 апреля 2011 года
Егор Ворожцов
10 / / 02.04.2011
Подскажите еще пожалуйста. Возник вопрос, можно ли как-нибудь получать новый размер файла, если дескриптор в течение времени не закрывается? т.е ОС не знает новый размер файла, пока он не закроется, и, соответственно, GetFileSize(...) возвращает одно и то же значение при каждом запуске.
278
03 апреля 2011 года
Alexander92
1.1K / / 04.08.2008
При правильном открытии файла GetFileSize() возвращает правильное значение при каждом новом вызове.
67K
03 апреля 2011 года
Егор Ворожцов
10 / / 02.04.2011
что-то не хочет((
Код:
// Функция 1-го потока - получаем и выводим число
// записанных в файл символов
static unsigned __stdcall funThread1(void *arg){
  int iDelay = 5000;
  DWORD dwM = dwWROperationsMaxNumber;
  //цикл потока
  while(dwM--){
    //cs-in
    if(SYCHRONIZATION_STATUS) EnterCriticalSection(&cs);
    hFile = CreateFile(SHARE_FILE_NAME, GENERIC_READ, 0,
        NULL, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, NULL);
    if(hFile != INVALID_HANDLE_VALUE){
      Form1->Memo1->Lines->Add((AnsiString)GetFileSize(hFile, NULL));
    }
    else{
      Form1->Memo1->Lines->Add(ERROR_OPENING_FILE);
    }
    CloseHandle((HANDLE)hFile);
    hFile=0;
    //cs-out
    if(SYCHRONIZATION_STATUS) LeaveCriticalSection(&cs);
    delay(iDelay);
  }
  return 0;
}

//-----------------------------------------

// Функция 2-го потока - запись в файл
static unsigned __stdcall funThread2(void *arg){
  delay(1000);
  int iDelay = 5000;
  DWORD
   dwM = dwWROperationsMaxNumber,
   dwPos,
   iBufSize = 10/*sizeof(STRING_TO_WRITE.c_str())*/,
   dwBytesWritten;
  //цикл потока
  while(dwM--){
    //cs-in
    if(SYCHRONIZATION_STATUS) EnterCriticalSection(&cs);
    hFile = CreateFile(SHARE_FILE_NAME, GENERIC_WRITE, 0,
        NULL, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, NULL);
    if(hFile != INVALID_HANDLE_VALUE){

      dwPos = SetFilePointer(hFile, 0, NULL, FILE_END);

      WriteFile(hFile, STRING_TO_WRITE.c_str(),
        iBufSize, &dwBytesWritten, NULL);

      dwTotalSymbolsWritten += /*dwBytesWritten*/iBufSize;
      Form1->Memo2->Lines->Add((AnsiString)dwTotalSymbolsWritten);
    }
    else{
      Form1->Memo2->Lines->Add(ERROR_OPENING_FILE);
    }
    CloseHandle((HANDLE)hFile);
    hFile=0;
    //cs-out
    if(SYCHRONIZATION_STATUS) LeaveCriticalSection(&cs);
    delay(iDelay);
  }
}


здесь 2 потока, один записывает в файл строку через интервал времени, другой - выводит размер файла.

Проблема в том, что попытки создать дескриптор файла неуспешны - в обоих случаях, как при записи, так и при попытке получения размера - CreateFile возвращает INVALID_HANDLE_VALUE.

Вторая проблема - программа завершается с ошибкой при включении синхронизации - т.е. когда флаг SYCHRONIZATION_STATUS = true. Но ведь именно обозначенная секция имхо является критической, т.к. там операции с файлом.

Помогите разобраться, что я сделал не так, я сам уже напрочь запутался((
67K
03 апреля 2011 года
Егор Ворожцов
10 / / 02.04.2011
Дополню: проблема с дескриптором появляется после первого использования файла и его закрытия (в любом из потоков). Создаваемые далее дескрипторы имеют значение INVALID_HANDLE_VALUE.
535
04 апреля 2011 года
Нездешний
537 / / 17.01.2008
2 вопроса:
1. Вы инициализируете критическую секцию перед ее использованием?
2. CreateFile с флагом CREATE_NEW возвращает INVALID_HANDLE_VALUE, если такой файл уже существует. Вы удаляете файл после каждого вызова?
67K
04 апреля 2011 года
Егор Ворожцов
10 / / 02.04.2011
все, разобрался) спасибо! заменил CREATE_NEW на OPEN_EXISTING
1.9K
05 апреля 2011 года
George22
91 / / 09.12.2007
Для того, чтобы убедиться, что синхронизация работает правильно можно
в одном потоке пикнуть: Beep(880,200);
Sleep(200);
в другом пикнуть Beep(920,200);
Sleep(200);
Очень удобно и глаза не напрягаются!
Реклама на сайте | Обмен ссылками | Ссылки | Экспорт (RSS) | Контакты
Добавить статью | Добавить исходник | Добавить хостинг-провайдера | Добавить сайт в каталог