Mutex不能与两个进程一起运行

时间:2012-02-06 22:38:42

标签: c winapi mutex semaphore createprocess

我使用win32 api在C编程 我的程序从void main开始,我做了一些创建具有特定名称的互斥锁的操作 然后使用INFINITE time参数在其上启动waitForSingleObject函数。

然后我通过createProcess函数启动一个EXE进程 EXE进程有一个类似的代码,现在正在使用与之前父进程相同的名称创建createMutex。

据我所知,我应该得到我在父程序中创建的相同互斥锁的句柄..因为它具有相同的名称。 所以在那之后,EXE代码也会在互斥锁句柄上再次执行WaitForSingleObject 具有相同的参数。

我原本预计会停下来等待,但它会继续发出信号,但是在这个阶段,我无法在任何地方发出信号。 我试图用0替换INFINITE参数,看看我是否得到WAIT_TIMEOUT但是这也不起作用。
为什么我的互斥体不起作用?

由于

添加相关代码:(我试图只放置相关的东西) *请注意EXE文件Process1包含一个代码,该代码执行openfileInDirectory,其文件名与我在void main中所做的相同,并且用于写入。 **我要遵循的互斥体叫做writeMutex。 FileSystemMutex是另一个与我当前问题无关的文件。

// Global variables definition from library header
void* viewVec;
HANDLE fileHandle;
int directoryLastBlockIndex;
FilesInProcessUse processFiles;          
HANDLE fileSystemMutex;
HANDLE filesAccessSemaphore;

void main()
{         

    FileDescriptor* fd, *fd2;
    int message,message2,message3;
    int processId = GetCurrentProcessId();
    char* input= NULL;

    /* print out our process ID */
    printf("Process %d reporting for duty\n",processId);


    fileSystemMutex = CreateMutex(NULL,FALSE,FILE_SYSTEM_MUTEX_NAME);
    printf("Process %d: After creating fileSystem mutex\n",processId);
    filesAccessSemaphore = CreateSemaphore(NULL,MAX_ACCESSORS_FOR_ALL_FILES,MAX_ACCESSORS_FOR_ALL_FILES,FILE_SYSTEM_SEMAPHORE_NAME);
    printf("Process %d: After creating filesAccessSemaphore\n",processId);

    initfs("C",NUM_OF_BLOCKS_IN_DISK,NUM_OF_BLOCKS_IN_DISK);

    viewVec = attachfs("C"); // Saving the address of the vector in global pointer.  

    if(viewVec!=NULL)
    {
        printf("Process %d: After AttachFS which succeded\n",processId);
        fd = (FileDescriptor*) createFileInDirectory("FileX",2,&message);
        if (fd!=NULL)
        {
            printf("Process %d:successfuly created the file: FileX in Drive C\n",processId);
        }
        else
        {
            printErrMessage(message);
        }
    }
    else
    {
        printf("Process %d: After AttachFS, which failed\n",processId);
    }

    fd = (FileDescriptor*) openFileInDirectory("FileX",READ_PERMISSION,&message);
    if(fd!=NULL)
    {
        printf("Process %d: opened FileXfile for read succefully",processId);
    }
    else
    {
        printf("Process %d:",processId);
        printErrMessage(message);
    }
    closeFileInDirectory(fd);
    fd = (FileDescriptor*) openFileInDirectory("FileX",WRITE_PERMISSION,&message);
    if(fd!=NULL)
    {
        printf("Process %d: opened FileXfile for write succefully",processId);
    }
    else
    {
        printf("Process %d:",processId);
        printErrMessage(message);
    }

    fd2 = (FileDescriptor*) openFileInDirectory("FileX",WRITE_PERMISSION,&message);
    if(fd!=NULL)
    {
        printf("Process %d: opened FileX file for write succefully",processId);
    }
    else
    {
        printf("Process %d:",processId);
        printErrMessage(message);
    }
}
}


void* openFileInDirectory(char* fileName, int ReadWriteFlag, int* out_ErrMessage)
{

    SystemInfoSection* sysInfo = readSystemInformationFromBeginingOfVector((char*)viewVec);
    DirectoryEntry* fileEntryInDirOffset;
    FileDescriptor* openfileDescriptor = NULL;
    int fileIndexInOpenFiles = 0;
    int writeRV;

    //Mark that another file is being processed 
    WaitForSingleObject(filesAccessSemaphore,INFINITE);


    //Check if the file exists else return error
    if(isFileAlreadyExisting(fileName, sysInfo->directoryStartBlockIndex, &fileEntryInDirOffset))
    {
        fileIndexInOpenFiles = getFileIndexInOpenFileDirectory(fileName);
        processFiles.allFilesVector[fileIndexInOpenFiles].accessSemaphore = CreateSemaphore(NULL,MAX_FILE_ACCESSORS,MAX_FILE_ACCESSORS,fileName);
        WaitForSingleObject(processFiles.allFilesVector[fileIndexInOpenFiles].accessSemaphore,INFINITE);
        if (ReadWriteFlag == WRITE_PERMISSION)
        {
            char writeMutexName[15];
            strcpy(writeMutexName, WRITE_MUTEX_PREFIX);
            strcat(writeMutexName, fileName);
            processFiles.allFilesVector[fileIndexInOpenFiles].writeMutex = CreateMutex(NULL,FALSE,writeMutexName);

            WaitForSingleObject(processFiles.allFilesVector[fileIndexInOpenFiles].writeMutex,INFINITE);

            //writeRV = WaitForSingleObject(processFiles.allFilesVector[fileIndexInOpenFiles].writeMutex,MAX_WAIT_TIMEOUT_IN_FS);
            //if(writeRV == WAIT_TIMEOUT)
            //{
            //  ReleaseSemaphore(processFiles.allFilesVector[fileIndexInOpenFiles].accessSemaphore,1,NULL);
            //  //return error indicating that another process is already writing to the file AND RETURN FROM THE FUNCTION
            //  *out_ErrMessage = ERR_FILE_IS_ALREADY_OPEN_TO_A_WRITE_BY_SOME_PROCESS;
            //  return openfileDescriptor;

            //}
        }

        processFiles.FDInProcessUseVector[fileIndexInOpenFiles].fileDirectoryEntry = fileEntryInDirOffset;
        processFiles.FDInProcessUseVector[fileIndexInOpenFiles].readWriteFlag = ReadWriteFlag;
        openfileDescriptor = &(processFiles.FDInProcessUseVector[fileIndexInOpenFiles]);
        processFiles.numOfFilesInUse++;


    }

    else
    {
        openfileDescriptor = NULL;
        *out_ErrMessage = ERR_FILE_NOT_FOUND;
    }
    free(sysInfo);

    return openfileDescriptor;
}

1 个答案:

答案 0 :(得分:4)

您可以使用CreateMutex function创建命名的全局互斥锁。

使用全局互斥锁的逻辑通常如下:

  1. 您尝试使用CreateMutex创建互斥锁。请注意“如果互斥锁是一个已命名的互斥锁,并且在此函数调用之前该对象存在,则返回值是现有对象的句柄”
  2. 使用WaitForSingleObject function
  3. 锁定(获取所有权)
  4. 使用ReleaseMutex function
  5. 解锁(释放所有权)
  6. CloseHandle返回CreateMutex function
  7. 这是C中的一个很好的例子:Using Mutex Objects

    您的代码中存在一些问题:

    1. 您没有释放writeMutex的所有权,这可能是此代码无法运行的主要原因。
    2. 您不会检查单个呼叫的返回值。您检查的唯一返回值是从函数返回的值。检查这些功能的文档,以便您可以正确处理可能的错误状态。
    3. CloseHandle您没有CreateMutex function返回。既不处理fileSystemMutex也不处理writeMutex.
    4. 您创建fileSystemMutex,但之后您永远不会使用它。这个互斥锁没有任何意义。