{"record":{"id":"64e340a84c1c0cbd","repo":"dotnet/runtime","slug":"comparison-failed-for-the-following-files-s","errorCode":null,"errorMessage":"Comparison failed for the following files(s): {}","messagePattern":"Comparison failed for the following files\\(s\\): (.+?)","errorType":"exception","errorClass":"RuntimeError","httpStatus":null,"severity":"error","filePath":"src/coreclr/scripts/utilities.py","lineNumber":96,"sourceCode":"    \"\"\"Updates dest directory with files from src directory\n\n    Args:\n        destpath (str): The destination path to sync with the source\n        srcpath (str): The source path to sync to the destination\n        recursive(boolean): If True, descend into and update subdirectories (default: True)\n        destructive(boolean): If True, delete files in the destination which do not exist in the source (default: True)\n        shallow(boolean): If True, only use os.stat to diff files. Do not examine contents (default: False)\n    \"\"\"\n    srcfiles, srcdirs = split_entries(os.listdir(srcpath), srcpath)\n    dstfiles, dstdirs = split_entries(os.listdir(dstpath), dstpath)\n\n\n    # Update files in both src and destination which are different in destination\n    commonfiles = srcfiles.intersection(dstfiles)\n    _, mismatches, errors = filecmp.cmpfiles(srcpath, dstpath, commonfiles, shallow=shallow)\n\n    if errors:\n        raise RuntimeError(\"Comparison failed for the following files(s): {}\".format(errors))\n\n    for mismatch in mismatches:\n        shutil.copyfile(os.path.join(srcpath, mismatch), os.path.join(dstpath, mismatch))\n\n    # Copy over files from source which do not exist in the destination\n    for missingfile in srcfiles.difference(dstfiles):\n        shutil.copyfile(os.path.join(srcpath, missingfile), os.path.join(dstpath, missingfile))\n\n    #If destructive, delete files in destination which do not exist in sourc\n    if destructive:\n        for deadfile in dstfiles.difference(srcfiles):\n            print(deadfile)\n            os.remove(os.path.join(dstpath, deadfile))\n\n        for deaddir in dstdirs.difference(srcdirs):\n            print(deaddir)\n            shutil.rmtree(os.path.join(dstpath, deaddir))\n","sourceCodeStart":78,"sourceCodeEnd":114,"githubUrl":"https://github.com/dotnet/runtime/blob/290d5ab72cc1102813fbc0406fb186ceadabc340/src/coreclr/scripts/utilities.py#L78-L114","documentation":"Raised by update_directory in utilities.py when filecmp.cmpfiles reports files in the `errors` list — files that exist in both src and dst but could not be compared (os.error on stat/read, permission denied, etc.). The directory sync aborts rather than silently skipping.","triggerScenarios":"A common file exists in src and dst but filecmp cannot stat or open it (EACCES, EIO, file locked on Windows, symlink loop, transient FS error).","commonSituations":"Windows file lock on a DLL being written; read-only permissions on dst; broken symlinks; network-mounted artifact dir with intermittent errors; antivirus locking the file mid-compare.","solutions":["Inspect the files in the error list for locks/permissions: `ls -l` and `stat` each.","Close any process holding the files (or disable AV locking) and rerun.","Fix permissions: `chmod -R u+rw <dst>` (or the offending side).","If a file is genuinely corrupt/unreadable, remove it from dst so update_directory copies it fresh."],"exampleFix":"// before\n# update_directory raises [197] with ['coreclr.dll']\n// after\nchmod u+rw <dst>/coreclr.dll  # or rm it; rerun update_directory","handlingStrategy":"validation","validationCode":"import os, stat\nfor f in commonfiles:\n    for side in (srcpath, dstpath):\n        p = os.path.join(side, f)\n        if not os.access(p, os.R_OK):\n            raise SystemExit(f'{p} not readable; fix perms before update_directory')","typeGuard":"def all_commonfiles_readable(commonfiles, srcpath, dstpath) -> bool:\n    import os\n    return all(os.access(os.path.join(s,f), os.R_OK) for f in commonfiles for s in (srcpath,dstpath))","tryCatchPattern":"try:\n    update_directory(src, dst)\nexcept RuntimeError as e:\n    if 'Comparison failed' in str(e):\n        import re; files = re.findall(r\"'([^']+)'\", str(e))\n        for f in files: os.chmod(os.path.join(dst,f), 0o644)\n        update_directory(src, dst)","preventionTips":["Ensure dst is writable and not locked before sync","Close processes holding files on Windows","Run syncs from an account with full perms"],"tags":["filesystem","permissions","utilities","windows-lock"],"analyzedSha":"290d5ab72cc1102813fbc0406fb186ceadabc340","analyzedAt":"2026-08-06T19:57:01.276Z","schemaVersion":2},"datasetVersion":"2026-08-06T23:17:07.152Z"}