cmake: Fix aom linkage race condition on MSVC

This commit fixes the linkers for both aom and aom_static writing the
export libraries to the same file on MSVC.

The fix also changes test_libaom, test_intra_pred_speed, and
lightfield_decoder to link against static aom because they rely
(undocumentedly, except for test_intra_pred_speed) on unexported AV1
functions.

Also allows to deduplicate AOM_SOURCES except on Xcode, which does not
support build targets made wholly of objects [1].

[1]: https://gitlab.kitware.com/cmake/cmake/-/issues/17500

BUG: aomedia:3401
Change-Id: Iedd97d6ac081872fe0093934345df05abe822273
diff --git a/CMakeLists.txt b/CMakeLists.txt
index dcaf7ce..f345bcd 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -273,11 +273,34 @@
   set(AOM_LIB_TARGETS ${AOM_LIB_TARGETS} aom_encoder_stats)
 endif()
 
-add_library(aom ${AOM_SOURCES} $<TARGET_OBJECTS:aom_rtcd>)
-if(BUILD_SHARED_LIBS)
-  add_library(aom_static STATIC ${AOM_SOURCES} $<TARGET_OBJECTS:aom_rtcd>)
-  set_target_properties(aom_static PROPERTIES OUTPUT_NAME aom)
+# Xcode generator cannot take a library composed solely of objects. See
+# https://gitlab.kitware.com/cmake/cmake/-/issues/17500
+if(XCODE)
+  set(target_objs_aom ${AOM_SOURCES})
+else()
+  add_library(aom_obj OBJECT ${AOM_SOURCES})
+  set(AOM_LIB_TARGETS ${AOM_LIB_TARGETS} aom_obj)
+  set(target_objs_aom $<TARGET_OBJECTS:aom_obj>)
+endif()
+add_library(aom ${target_objs_aom} $<TARGET_OBJECTS:aom_rtcd>)
 
+if(BUILD_SHARED_LIBS)
+  add_library(aom_static STATIC ${target_objs_aom} $<TARGET_OBJECTS:aom_rtcd>)
+  if(MSVC OR (WIN32 AND NOT MINGW))
+    # Fix race condition on the export library file between the two versions.
+    # Affects MSVC in all three flavors (stock, Clang/CL, LLVM-- the latter sets
+    # MSVC and MINGW both to FALSE).
+    set_target_properties(aom PROPERTIES ARCHIVE_OUTPUT_NAME "aom_shared")
+  endif()
+  # Tests and examples rely on having unexported AV1 symbols visible. This is
+  # not the case on Windows platforms due to enforcement of the module
+  # definition file.
+  set(AOM_LIB aom_static)
+else()
+  set(AOM_LIB aom)
+endif()
+
+if(BUILD_SHARED_LIBS)
   if(NOT MSVC)
     # Extract version string and set VERSION/SOVERSION for the aom target.
     extract_version_string("${AOM_CONFIG_DIR}/config/aom_version.h"
@@ -339,9 +362,9 @@
 setup_av1_targets()
 
 # Make all library targets depend on aom_rtcd to make sure it builds first.
-foreach(aom_lib ${AOM_LIB_TARGETS})
-  if(NOT "${aom_lib}" STREQUAL "aom_rtcd")
-    add_dependencies(${aom_lib} aom_rtcd)
+foreach(aom_tgt ${AOM_LIB_TARGETS})
+  if(NOT "${aom_tgt}" STREQUAL "aom_rtcd")
+    add_dependencies(${aom_tgt} aom_rtcd)
   endif()
 endforeach()
 
@@ -713,7 +736,7 @@
 endif()
 
 foreach(aom_app ${AOM_APP_TARGETS})
-  target_link_libraries(${aom_app} ${AOM_LIB_LINK_TYPE} aom)
+  target_link_libraries(${aom_app} ${AOM_LIB_LINK_TYPE} ${AOM_LIB})
 endforeach()
 
 if(ENABLE_EXAMPLES OR ENABLE_TESTS OR ENABLE_TOOLS)
diff --git a/test/test.cmake b/test/test.cmake
index 01ed659..685d0e3 100644
--- a/test/test.cmake
+++ b/test/test.cmake
@@ -478,19 +478,16 @@
       target_sources(test_libaom PRIVATE ${AOM_ENCODE_PERF_TEST_SOURCES})
     endif()
 
-    if(NOT BUILD_SHARED_LIBS)
-      add_executable(test_intra_pred_speed
-                     ${AOM_TEST_INTRA_PRED_SPEED_SOURCES}
-                     $<TARGET_OBJECTS:aom_common_app_util>)
-      set_property(TARGET test_intra_pred_speed
-                   PROPERTY FOLDER ${AOM_IDE_TEST_FOLDER})
-      target_link_libraries(test_intra_pred_speed ${AOM_LIB_LINK_TYPE} aom
-                            aom_gtest)
-      list(APPEND AOM_APP_TARGETS test_intra_pred_speed)
-    endif()
+    add_executable(test_intra_pred_speed ${AOM_TEST_INTRA_PRED_SPEED_SOURCES}
+                                         $<TARGET_OBJECTS:aom_common_app_util>)
+    set_property(TARGET test_intra_pred_speed
+                 PROPERTY FOLDER ${AOM_IDE_TEST_FOLDER})
+    target_link_libraries(test_intra_pred_speed ${AOM_LIB_LINK_TYPE} ${AOM_LIB}
+                          aom_gtest)
+    list(APPEND AOM_APP_TARGETS test_intra_pred_speed)
   endif()
 
-  target_link_libraries(test_libaom ${AOM_LIB_LINK_TYPE} aom aom_gtest)
+  target_link_libraries(test_libaom ${AOM_LIB_LINK_TYPE} ${AOM_LIB} aom_gtest)
 
   if(CONFIG_LIBYUV)
     target_sources(test_libaom PRIVATE $<TARGET_OBJECTS:yuv>)