@@ -365,6 +365,33 @@ extension IncrementalCompilationTests {
365365 XCTAssertFalse ( mandatoryJobInputs. contains ( " other.swift " ) )
366366 }
367367
368+ // Source file timestamps updated but contents are the same, with file-hashing emit-module job should be skipped
369+ func testNullBuildNoEmitModuleWithHashing( ) throws {
370+ let extraArguments = [ " -experimental-emit-module-separately " , " -emit-module " , " -enable-incremental-file-hashing " ]
371+ try buildInitialState ( extraArguments: extraArguments)
372+ touch ( " main " )
373+ touch ( " other " )
374+ touch ( try AbsolutePath ( validating: explicitSwiftDependenciesPath. appending ( component: " E.swiftinterface " ) . pathString) )
375+ let driver = try doABuildWithoutExpectations ( arguments: commonArgs + extraArguments + ( try XCTUnwrap ( Driver . sdkArgumentsForTesting ( ) ) ) )
376+ let mandatoryJobs = try XCTUnwrap ( driver. incrementalCompilationState? . mandatoryJobsInOrder)
377+ let mandatoryJobInputs = mandatoryJobs. flatMap { $0. inputs } . map { $0. file. basename }
378+ XCTAssertFalse ( mandatoryJobs. contains { $0. kind == . emitModule } , " emit-module should be skipped when using hashes and content unchanged " )
379+ XCTAssertFalse ( mandatoryJobInputs. contains ( " main.swift " ) )
380+ XCTAssertFalse ( mandatoryJobInputs. contains ( " other.swift " ) )
381+ }
382+
383+ // Source file updated, emit-module job should not be skipped regardless of file-hashing
384+ func testEmitModuleWithHashingWhenContentChanges( ) throws {
385+ let extraArguments = [ " -experimental-emit-module-separately " , " -emit-module " , " -enable-incremental-file-hashing " ]
386+ try buildInitialState ( extraArguments: extraArguments)
387+ replace ( contentsOf: " main " , with: " let foo = 2 " )
388+ let driver = try doABuildWithoutExpectations ( arguments: commonArgs + extraArguments + ( try XCTUnwrap ( Driver . sdkArgumentsForTesting ( ) ) ) )
389+ let mandatoryJobs = try XCTUnwrap ( driver. incrementalCompilationState? . mandatoryJobsInOrder)
390+ let mandatoryJobInputs = mandatoryJobs. flatMap { $0. inputs } . map { $0. file. basename }
391+ XCTAssertTrue ( mandatoryJobs. contains { $0. kind == . emitModule } , " emit-module should run when using hashes and content has changed " )
392+ XCTAssertTrue ( mandatoryJobInputs. contains ( " main.swift " ) )
393+ }
394+
368395 // External deps timestamp updated but contents are the same, and file-hashing is explicitly disabled
369396 func testExplicitIncrementalBuildExternalDepsWithoutHashing( ) throws {
370397 replace ( contentsOf: " other " , with: " import E;let bar = foo " )
0 commit comments