diff --git a/configure b/configure
index f115b21064..f16fbb320a 100755
--- a/configure
+++ b/configure
@@ -3129,8 +3129,8 @@ wmv3_vaapi_hwaccel_select="vc1_vaapi_hwaccel"
  wmv3_vdpau_hwaccel_select="vc1_vdpau_hwaccel"
   # hardware-accelerated codecs
-mediafoundation_deps="mftransform_h MFCreateAlignedMemoryBuffer"
-mediafoundation_extralibs="-lmfplat -lmfuuid -lole32 -lstrmiids"
+mediafoundation_deps="LoadLibrary mftransform_h 
MFCreateAlignedMemoryBuffer"
+mediafoundation_extralibs="-lole32 -lstrmiids"
  omx_deps="libdl pthreads"
  omx_rpi_select="omx"
  qsv_deps="libmfx"
diff --git a/libavcodec/mf_utils.c b/libavcodec/mf_utils.c
index eeabd0ce0b..9a83f71692 100644
--- a/libavcodec/mf_utils.c
+++ b/libavcodec/mf_utils.c
@@ -106,19 +106,20 @@ char *ff_hr_str_buf(char *buf, size_t size, 
HRESULT hr)
  // If fill_data!=NULL, initialize the buffer and set the length. (This 
is a
  // subtle but important difference: some decoders want CurrentLength==0 on
  // provided output buffers.)
-IMFSample *ff_create_memory_sample(void *fill_data, size_t size, size_t 
align)
+IMFSample *ff_create_memory_sample(const MFSymbols *symbols, void 
*fill_data,
+                                   size_t size, size_t align)
  {
      HRESULT hr;
      IMFSample *sample;
      IMFMediaBuffer *buffer;
  -    hr = MFCreateSample(&sample);
+    hr = symbols->MFCreateSample(&sample);
      if (FAILED(hr))
          return NULL;
       align = FFMAX(align, 16); // 16 is "recommended", even if not 
required
  -    hr = MFCreateAlignedMemoryBuffer(size, align - 1, &buffer);
+    hr = symbols->MFCreateAlignedMemoryBuffer(size, align - 1, &buffer);
      if (FAILED(hr))
          return NULL;
  @@ -548,7 +549,7 @@ const CLSID *ff_codec_to_mf_subtype(enum AVCodecID 
codec)
      }
  }
  -static int init_com_mf(void *log)
+static int init_com_mf(const MFSymbols *symbols, void *log)
  {
      HRESULT hr;
  @@ -561,7 +562,7 @@ static int init_com_mf(void *log)
          return AVERROR(ENOSYS);
      }
  -    hr = MFStartup(MF_VERSION, MFSTARTUP_FULL);
+    hr = symbols->MFStartup(MF_VERSION, MFSTARTUP_FULL);
      if (FAILED(hr)) {
          av_log(log, AV_LOG_ERROR, "could not initialize 
MediaFoundation\n");
          CoUninitialize();
@@ -571,15 +572,16 @@ static int init_com_mf(void *log)
      return 0;
  }
  -static void uninit_com_mf(void)
+static void uninit_com_mf(const MFSymbols *symbols)
  {
-    MFShutdown();
+    symbols->MFShutdown();
      CoUninitialize();
  }
   // Find and create a IMFTransform with the given input/output types. 
When done,
  // you should use ff_free_mf() to destroy it, which will also uninit COM.
-int ff_instantiate_mf(void *log,
+int ff_instantiate_mf(const MFSymbols *symbols,
+                      void *log,
                        GUID category,
                        MFT_REGISTER_TYPE_INFO *in_type,
                        MFT_REGISTER_TYPE_INFO *out_type,
@@ -594,7 +596,7 @@ int ff_instantiate_mf(void *log,
      IMFActivate *winner = 0;
      UINT32 flags;
  -    ret = init_com_mf(log);
+    ret = init_com_mf(symbols, log);
      if (ret < 0)
          return ret;
  @@ -667,14 +669,14 @@ int ff_instantiate_mf(void *log,
      return 0;
   error_uninit_mf:
-    uninit_com_mf();
+    uninit_com_mf(symbols);
      return AVERROR(ENOSYS);
  }
  -void ff_free_mf(IMFTransform **mft)
+void ff_free_mf(const MFSymbols *symbols, IMFTransform **mft)
  {
      if (*mft)
          IMFTransform_Release(*mft);
      *mft = NULL;
-    uninit_com_mf();
+    uninit_com_mf(symbols);
  }
diff --git a/libavcodec/mf_utils.h b/libavcodec/mf_utils.h
index d514723c3b..1b1041bb29 100644
--- a/libavcodec/mf_utils.h
+++ b/libavcodec/mf_utils.h
@@ -41,6 +41,15 @@
   #include "avcodec.h"
  +typedef struct MFSymbols {
+    HRESULT (*MFCreateSample) (IMFSample **ppIMFSample);
+    HRESULT (*MFCreateAlignedMemoryBuffer) (DWORD cbMaxLength, DWORD 
cbAligment,
+                                            IMFMediaBuffer **ppBuffer);
+    HRESULT (*MFStartup) (ULONG Version, DWORD dwFlags);
+    HRESULT (*MFShutdown) (void);
+    HRESULT (*MFCreateMediaType) (IMFMediaType **ppMFType);
+} MFSymbols;
+
  // These functions do exist in mfapi.h, but are only available within
  // __cplusplus ifdefs.
  HRESULT ff_MFGetAttributeSize(IMFAttributes *pattr, REFGUID guid,
@@ -150,7 +159,8 @@ char *ff_hr_str_buf(char *buf, size_t size, HRESULT hr);
  #define FF_VAL_VT_UI4(v) FF_VARIANT_VALUE(VT_UI4, .ulVal = (v))
  #define FF_VAL_VT_BOOL(v) FF_VARIANT_VALUE(VT_BOOL, .boolVal = (v))
  -IMFSample *ff_create_memory_sample(void *fill_data, size_t size, 
size_t align);
+IMFSample *ff_create_memory_sample(const MFSymbols *symbols, void 
*fill_data,
+                                   size_t size, size_t align);
  enum AVSampleFormat ff_media_type_to_sample_fmt(IMFAttributes *type);
  enum AVPixelFormat ff_media_type_to_pix_fmt(IMFAttributes *type);
  const GUID *ff_pix_fmt_to_guid(enum AVPixelFormat pix_fmt);
@@ -160,10 +170,10 @@ char *ff_guid_str_buf(char *buf, size_t buf_size, 
const GUID *guid);
  void ff_attributes_dump(void *log, IMFAttributes *attrs);
  void ff_media_type_dump(void *log, IMFMediaType *type);
  const CLSID *ff_codec_to_mf_subtype(enum AVCodecID codec);
-int ff_instantiate_mf(void *log, GUID category,
+int ff_instantiate_mf(const MFSymbols *symbols, void *log, GUID category,
                        MFT_REGISTER_TYPE_INFO *in_type,
                        MFT_REGISTER_TYPE_INFO *out_type,
                        int use_hw, IMFTransform **res);
-void ff_free_mf(IMFTransform **mft);
+void ff_free_mf(const MFSymbols *symbols, IMFTransform **mft);
   #endif
diff --git a/libavcodec/mfenc.c b/libavcodec/mfenc.c
index 280941cf2e..0444d5af38 100644
--- a/libavcodec/mfenc.c
+++ b/libavcodec/mfenc.c
@@ -29,9 +29,12 @@
  #include "libavutil/time.h"
  #include "codec_internal.h"
  #include "internal.h"
+#include "compat/w32dlfcn.h"
   typedef struct MFContext {
      AVClass *av_class;
+    void *library;
+    MFSymbols symbols;
      AVFrame *frame;
      int is_video, is_audio;
      GUID main_subtype;
@@ -292,7 +295,7 @@ static IMFSample 
