Ejemplo n.º 1
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.name in ('Map', 'Unmap'):
            # On D3D11 Map/Unmap is not a resource method, but a context method instead.
            resourceArg = method.getArgByName('pResource')
            if resourceArg is None:
                pResource = 'this'
            else:
                wrapperInterfaceName = getWrapperInterfaceName(resourceArg.type.type)
                print '    %s * _pResource = static_cast<%s*>(%s);' % (wrapperInterfaceName, wrapperInterfaceName, resourceArg.name)
                pResource = '_pResource'

        if method.name == 'Unmap':
            print '    _MAP_DESC _MapDesc = %s->_MapDesc;' % pResource
            #print r'    os::log("%%p -> %%p+%%lu\n", %s,_MapDesc.pData, (unsigned long)_MapDesc.Size);' % pResource
            print '    if (_MapDesc.Size && _MapDesc.pData) {'
            self.emit_memcpy('_MapDesc.pData', '_MapDesc.Size')
            print '    }'

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base, method)

        if method.name == 'Map':
            # NOTE: recursive locks are explicitely forbidden
            print '    _MAP_DESC _MapDesc;'
            print '    if (SUCCEEDED(_result)) {'
            print '        _getMapDesc(_this, %s, _MapDesc);' % ', '.join(method.argNames())
            print '    } else {'
            print '        _MapDesc.pData = NULL;'
            print '        _MapDesc.Size = 0;'
            print '    }'
            #print r'    os::log("%%p <- %%p+%%lu\n", %s,_MapDesc.pData, (unsigned long)_MapDesc.Size);' % pResource
            print '    %s->_MapDesc = _MapDesc;' % pResource
Ejemplo n.º 2
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.name in ('Map', 'Unmap'):
            # On D3D11 Map/Unmap is not a resource method, but a context method instead.
            resourceArg = method.getArgByName('pResource')
            if resourceArg is None:
                print '    _MAP_DESC & _MapDesc = m_MapDesc;'
            else:
                print '    _MAP_DESC & _MapDesc = m_MapDescs[std::pair<%s, UINT>(pResource, Subresource)];' % resourceArg.type

        if method.name == 'Unmap':
            print '    if (_MapDesc.Size && _MapDesc.pData) {'
            self.emit_memcpy('_MapDesc.pData', '_MapDesc.Size')
            print '    }'

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base,
                                                      method)

        if method.name == 'Map':
            # NOTE: recursive locks are explicitely forbidden
            print '    if (SUCCEEDED(_result)) {'
            print '        _getMapDesc(_this, %s, _MapDesc);' % ', '.join(
                method.argNames())
            print '    } else {'
            print '        _MapDesc.pData = NULL;'
            print '        _MapDesc.Size = 0;'
            print '    }'
Ejemplo n.º 3
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.getArgByName('pInitialData'):
            pDesc1 = method.getArgByName('pDesc1')
            if pDesc1 is not None:
                print r'    %s pDesc = pDesc1;' % (pDesc1.type,)

        if method.name in ('Map', 'Unmap'):
            # On D3D11 Map/Unmap is not a resource method, but a context method instead.
            resourceArg = method.getArgByName('pResource')
            if resourceArg is None:
                print '    _MAP_DESC & _MapDesc = m_MapDesc;'
                print '    MemoryShadow & _MapShadow = m_MapShadow;'
                print '    %s *pResourceInstance = m_pInstance;' % interface.name
            else:
                print '    _MAP_DESC & _MapDesc = m_MapDescs[std::pair<%s, UINT>(pResource, Subresource)];' % resourceArg.type
                print '    MemoryShadow & _MapShadow = m_MapShadows[std::pair<%s, UINT>(pResource, Subresource)];' % resourceArg.type
                print '    Wrap%spResourceInstance = static_cast<Wrap%s>(%s);' % (resourceArg.type, resourceArg.type, resourceArg.name)

        if method.name == 'Unmap':
            print '    if (_MapDesc.Size && _MapDesc.pData) {'
            print '        if (_shouldShadowMap(pResourceInstance)) {'
            print '            _MapShadow.update(trace::fakeMemcpy);'
            print '        } else {'
            self.emit_memcpy('_MapDesc.pData', '_MapDesc.Size')
            print '        }'
            print '    }'

        if interface.hasBase(d3d11.ID3D11VideoContext) and \
           method.name == 'ReleaseDecoderBuffer':
            print '    std::map<UINT, std::pair<void *, UINT> >::iterator it = m_MapDesc.find(Type);'
            print '    if (it != m_MapDesc.end()) {'
            self.emit_memcpy('it->second.first', 'it->second.second')
            print '        m_MapDesc.erase(it);'
            print '    }'

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base, method)

        if method.name == 'Map':
            # NOTE: recursive locks are explicitely forbidden
            print '    if (SUCCEEDED(_result)) {'
            print '        _getMapDesc(_this, %s, _MapDesc);' % ', '.join(method.argNames())
            print '        if (_MapDesc.pData && _shouldShadowMap(pResourceInstance)) {'
            if interface.name.startswith('IDXGI'):
                print '            (void)_MapShadow;'
            else:
                print '            bool _discard = MapType == 4 /* D3D1[01]_MAP_WRITE_DISCARD */;'
                print '            _MapShadow.cover(_MapDesc.pData, _MapDesc.Size, _discard);'
            print '        }'
            print '    } else {'
            print '        _MapDesc.pData = NULL;'
            print '        _MapDesc.Size = 0;'
            print '    }'

        if interface.hasBase(d3d11.ID3D11VideoContext) and \
           method.name == 'GetDecoderBuffer':
            print '    if (SUCCEEDED(_result)) {'
            print '        m_MapDesc[Type] = std::make_pair(*ppBuffer, *pBufferSize);'
            print '    } else {'
            print '        m_MapDesc[Type] = std::make_pair(nullptr, 0);'
            print '    }'
Ejemplo n.º 4
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.name in ('Unlock', 'UnlockRect', 'UnlockBox'):
            if interface.name in ['IDirect3DTexture9']:
                print '    std::map<UINT, std::pair<size_t, VOID *> >::iterator it = _MappedData.find(Level);'
                print '    if (it != _MappedData.end()) {'
                self.emit_memcpy('(LPBYTE)it->second.second', 'it->second.first')
                print '        _MappedData.erase(it);'
                print '    }'
            else:
                print '    if (_MappedSize && m_pbData) {'
                self.emit_memcpy('(LPBYTE)m_pbData', '_MappedSize')
                print '    }'

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base, method)

        if method.name in ('Lock', 'LockRect', 'LockBox'):
            if interface.name in ['IDirect3DTexture9']:
                print '    if (SUCCEEDED(_result) && !(Flags & D3DLOCK_READONLY)) {'
                print '        size_t mappedSize;'
                print '        VOID * pbData;'
                print '        _getMapInfo(_this, %s, pbData, mappedSize);' % ', '.join(method.argNames()[:-1])
                print '        _MappedData[Level] = std::make_pair(mappedSize, pbData);'
                print '    } else {'
                print '        _MappedData.erase(Level);'
                print '    }'
            else:
                # FIXME: handle recursive locks
                print '    if (SUCCEEDED(_result) && !(Flags & D3DLOCK_READONLY)) {'
                print '        _getMapInfo(_this, %s, m_pbData, _MappedSize);' % ', '.join(method.argNames()[:-1])
                print '    } else {'
                print '        m_pbData = NULL;'
                print '        _MappedSize = 0;'
                print '    }'
Ejemplo n.º 5
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.name in ('Unlock', 'UnlockRect', 'UnlockBox'):
            print '    if (_MappedSize && m_pbData) {'
            self.emit_memcpy('(LPBYTE)m_pbData', '_MappedSize')
            print '    }'

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base, method)

        if method.name in ('Lock', 'LockRect', 'LockBox'):
            # FIXME: handle recursive locks
            print '    if (SUCCEEDED(_result) && !(Flags & D3DLOCK_READONLY)) {'
            print '        _getMapInfo(_this, %s, m_pbData, _MappedSize);' % ', '.join(method.argNames()[:-1])
            print '    } else {'
            print '        m_pbData = NULL;'
            print '        _MappedSize = 0;'
            print '    }'

        # Clamp capabilities
        if method.name == 'GetDeviceCaps':
            print '    if (SUCCEEDED(_result)) {'
            print '         clampCaps(pCaps);'
            print '    }'
        if method.name == 'CheckDeviceFormat':
            print '    if (SUCCEEDED(_result)) {'
            print '         if (!clampFormat(Usage, RType, CheckFormat)) {'
            print '             _result = D3DERR_NOTAVAILABLE;'
            print '         }'
            print '    }'
        if method.name == 'CheckDeviceMultiSampleType':
            print '    if (SUCCEEDED(_result)) {'
            print '         if (!clampMultiSampleType(SurfaceFormat, MultiSampleType, pQualityLevels)) {'
            print '             _result = D3DERR_NOTAVAILABLE;'
            print '         }'
            print '    }'
Ejemplo n.º 6
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.getArgByName('pInitialData'):
            pDesc1 = method.getArgByName('pDesc1')
            if pDesc1 is not None:
                print r'    %s pDesc = pDesc1;' % (pDesc1.type,)

        if method.name in ('Map', 'Unmap'):
            # On D3D11 Map/Unmap is not a resource method, but a context method instead.
            resourceArg = method.getArgByName('pResource')
            if resourceArg is None:
                print '    _MAP_DESC & _MapDesc = m_MapDesc;'
            else:
                print '    _MAP_DESC & _MapDesc = m_MapDescs[std::pair<%s, UINT>(pResource, Subresource)];' % resourceArg.type

        if method.name == 'Unmap':
            print '    if (_MapDesc.Size && _MapDesc.pData) {'
            self.emit_memcpy('_MapDesc.pData', '_MapDesc.Size')
            print '    }'

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base, method)

        if method.name == 'Map':
            # NOTE: recursive locks are explicitely forbidden
            print '    if (SUCCEEDED(_result)) {'
            print '        _getMapDesc(_this, %s, _MapDesc);' % ', '.join(method.argNames())
            print '    } else {'
            print '        _MapDesc.pData = NULL;'
            print '        _MapDesc.Size = 0;'
            print '    }'
Ejemplo n.º 7
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.name in ('Unlock', 'UnlockRect', 'UnlockBox'):
            if interface.base.name == 'IDirect3DBaseTexture9':
                assert method.getArgByName('Level') is not None
                print '    std::map<UINT, std::pair<size_t, VOID *> >::iterator it = _MappedData.find(Level);'
                print '    if (it != _MappedData.end()) {'
                self.emit_memcpy('(LPBYTE)it->second.second', 'it->second.first')
                print '        _MappedData.erase(it);'
                print '    }'
            else:
                assert method.getArgByName('Level') is None
                print '    if (_MappedSize && m_pbData) {'
                self.emit_memcpy('(LPBYTE)m_pbData', '_MappedSize')
                print '    }'

        if interface.name == 'IDirectXVideoDecoder' and method.name == 'ReleaseBuffer':
            print '    std::map<UINT, std::pair<void *, UINT> >::iterator it = _MappedData.find(BufferType);'
            print '    if (it != _MappedData.end()) {'
            self.emit_memcpy('it->second.first', 'it->second.second')
            print '        _MappedData.erase(it);'
            print '    }'

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base, method)

        if method.name in ('Lock', 'LockRect', 'LockBox'):
            if interface.base.name == 'IDirect3DBaseTexture9':
                assert method.getArgByName('Level') is not None
                print '    if (SUCCEEDED(_result) && !(Flags & D3DLOCK_READONLY)) {'
                print '        size_t mappedSize;'
                print '        VOID * pbData;'
                print '        _getMapInfo(_this, %s, pbData, mappedSize);' % ', '.join(method.argNames()[:-1])
                print '        _MappedData[Level] = std::make_pair(mappedSize, pbData);'
                print '    } else {'
                print '        _MappedData.erase(Level);'
                print '    }'
            else:
                # FIXME: handle recursive locks
                assert method.getArgByName('Level') is None
                if method.name == 'Lock':
                    # Ignore D3DLOCK_READONLY for buffers.
                    # https://github.com/apitrace/apitrace/issues/435
                    print '    if (SUCCEEDED(_result)) {'
                else:
                    print '    if (SUCCEEDED(_result) && !(Flags & D3DLOCK_READONLY)) {'
                print '        _getMapInfo(_this, %s, m_pbData, _MappedSize);' % ', '.join(method.argNames()[:-1])
                print '    } else {'
                print '        m_pbData = NULL;'
                print '        _MappedSize = 0;'
                print '    }'

        if interface.name == 'IDirectXVideoDecoder' and method.name == 'GetBuffer':
            print '    if (SUCCEEDED(_result)) {'
            print '        _MappedData[BufferType] = std::make_pair(*ppBuffer, *pBufferSize);'
            print '    } else {'
            print '        _MappedData[BufferType] = std::make_pair(nullptr, 0);'
            print '    }'
Ejemplo n.º 8
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.name in ('Unlock', 'UnlockRect', 'UnlockBox'):
            print '    if (_MappedSize && m_pbData) {'
            self.emit_memcpy('(LPBYTE)m_pbData', '_MappedSize')
            print '    }'

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base, method)

        if method.name in ('Lock', 'LockRect', 'LockBox'):
            # FIXME: handle recursive locks
            print '    if (SUCCEEDED(_result) && !(Flags & D3DLOCK_READONLY)) {'
            print '        _getMapInfo(_this, %s, m_pbData, _MappedSize);' % ', '.join(method.argNames()[:-1])
            print '    } else {'
            print '        m_pbData = NULL;'
            print '        _MappedSize = 0;'
            print '    }'
Ejemplo n.º 9
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.name == 'Unmap':
            print '    if (_MappedSize && _pMappedData) {'
            self.emit_memcpy('_pMappedData', '_pMappedData', '_MappedSize')
            print '    }'

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base, method)

        if method.name == 'Map':
            # NOTE: recursive locks are explicitely forbidden
            print '    if (SUCCEEDED(_result)) {'
            print '        _getMapInfo(_this, %s, _pMappedData, _MappedSize);' % ', '.join(method.argNames())
            print '    } else {'
            print '        _pMappedData = NULL;'
            print '        _MappedSize = 0;'
            print '    }'
Ejemplo n.º 10
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.name in ('Unlock', 'UnlockRect', 'UnlockBox'):
            print('    if (_MappedSize && m_pbData) {')
            self.emit_memcpy('(LPBYTE)m_pbData', '_MappedSize')
            print('    }')

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base, method)

        if method.name in ('Lock', 'LockRect', 'LockBox'):
            # FIXME: handle recursive locks
            print('    if (SUCCEEDED(_result) && !(Flags & D3DLOCK_READONLY)) {')
            print('        _getMapInfo(_this, %s, m_pbData, _MappedSize);' % ', '.join(method.argNames()[:-1]))
            print('    } else {')
            print('        m_pbData = NULL;')
            print('        _MappedSize = 0;')
            print('    }')
Ejemplo n.º 11
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.name == 'Unmap':
            print '    if (_MappedSize && _pMappedData) {'
            self.emit_memcpy('_pMappedData', '_pMappedData', '_MappedSize')
            print '    }'

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base,
                                                      method)

        if method.name == 'Map':
            # NOTE: recursive locks are explicitely forbidden
            print '    if (SUCCEEDED(_result)) {'
            print '        _getMapInfo(_this, %s, _pMappedData, _MappedSize);' % ', '.join(
                method.argNames())
            print '    } else {'
            print '        _pMappedData = NULL;'
            print '        _MappedSize = 0;'
            print '    }'
Ejemplo n.º 12
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if interface.name == "IDirect3DVertexBuffer9" and method.name == "Unlock":
            print "    if (m_pbData) {"
            self.emit_memcpy("(LPBYTE)m_pbData", "(LPBYTE)m_pbData", "m_SizeToLock")
            print "    }"

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base, method)

        if interface.name == "IDirect3DVertexBuffer9" and method.name == "Lock":
            # FIXME: handle recursive locks
            print "    if (__result == D3D_OK && !(Flags & D3DLOCK_READONLY)) {"
            print "        if (SizeToLock) {"
            print "            m_SizeToLock = SizeToLock;"
            print "        } else {"
            print "            D3DVERTEXBUFFER_DESC Desc;"
            print "            m_pInstance->GetDesc(&Desc);"
            print "            m_SizeToLock = Desc.Size;"
            print "        }"
            print "        m_pbData = *ppbData;"
            print "    } else {"
            print "        m_pbData = NULL;"
            print "    }"
Ejemplo n.º 13
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if interface.name == 'IDirect3DVertexBuffer9' and method.name == 'Unlock':
            print '    if (m_pbData) {'
            self.emit_memcpy('(LPBYTE)m_pbData', '(LPBYTE)m_pbData', 'm_SizeToLock')
            print '    }'

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base, method)

        if interface.name == 'IDirect3DVertexBuffer9' and method.name == 'Lock':
            # FIXME: handle recursive locks
            print '    if (__result == D3D_OK && !(Flags & D3DLOCK_READONLY)) {'
            print '        if (SizeToLock) {'
            print '            m_SizeToLock = SizeToLock;'
            print '        } else {'
            print '            D3DVERTEXBUFFER_DESC Desc;'
            print '            m_pInstance->GetDesc(&Desc);'
            print '            m_SizeToLock = Desc.Size;'
            print '        }'
            print '        m_pbData = *ppbData;'
            print '    } else {'
            print '        m_pbData = NULL;'
            print '    }'
Ejemplo n.º 14
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.name in ('Unlock', 'UnlockRect', 'UnlockBox'):
            if interface.name in ['IDirect3DTexture9']:
                print '    std::map<UINT, std::pair<size_t, VOID *> >::iterator it = _MappedData.find(Level);'
                print '    if (it != _MappedData.end()) {'
                self.emit_memcpy('(LPBYTE)it->second.second',
                                 'it->second.first')
                print '        _MappedData.erase(it);'
                print '    }'
            else:
                print '    if (_MappedSize && m_pbData) {'
                self.emit_memcpy('(LPBYTE)m_pbData', '_MappedSize')
                print '    }'

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base,
                                                      method)

        if method.name in ('Lock', 'LockRect', 'LockBox'):
            if interface.name in ['IDirect3DTexture9']:
                print '    if (SUCCEEDED(_result) && !(Flags & D3DLOCK_READONLY)) {'
                print '        size_t mappedSize;'
                print '        VOID * pbData;'
                print '        _getMapInfo(_this, %s, pbData, mappedSize);' % ', '.join(
                    method.argNames()[:-1])
                print '        _MappedData[Level] = std::make_pair(mappedSize, pbData);'
                print '    } else {'
                print '        _MappedData.erase(Level);'
                print '    }'
            else:
                # FIXME: handle recursive locks
                print '    if (SUCCEEDED(_result) && !(Flags & D3DLOCK_READONLY)) {'
                print '        _getMapInfo(_this, %s, m_pbData, _MappedSize);' % ', '.join(
                    method.argNames()[:-1])
                print '    } else {'
                print '        m_pbData = NULL;'
                print '        _MappedSize = 0;'
                print '    }'
Ejemplo n.º 15
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.name in ('Unlock', 'UnlockRect', 'UnlockBox'):
            print '    if (_MappedSize && m_pbData) {'
            self.emit_memcpy('(LPBYTE)m_pbData', '_MappedSize')
            print '    }'

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base,
                                                      method)

        if method.name in ('Lock', 'LockRect', 'LockBox'):
            # FIXME: handle recursive locks
            print '    if (SUCCEEDED(_result) && !(Flags & D3DLOCK_READONLY)) {'
            print '        _getMapInfo(_this, %s, m_pbData, _MappedSize);' % ', '.join(
                method.argNames()[:-1])
            print '    } else {'
            print '        m_pbData = NULL;'
            print '        _MappedSize = 0;'
            print '    }'

        # Clamp capabilities
        if method.name == 'GetDeviceCaps':
            print '    if (SUCCEEDED(_result)) {'
            print '         clampCaps(pCaps);'
            print '    }'
        if method.name == 'CheckDeviceFormat':
            print '    if (SUCCEEDED(_result)) {'
            print '         if (!clampFormat(Usage, RType, CheckFormat)) {'
            print '             _result = D3DERR_NOTAVAILABLE;'
            print '         }'
            print '    }'
        if method.name == 'CheckDeviceMultiSampleType':
            print '    if (SUCCEEDED(_result)) {'
            print '         if (!clampMultiSampleType(SurfaceFormat, MultiSampleType, pQualityLevels)) {'
            print '             _result = D3DERR_NOTAVAILABLE;'
            print '         }'
            print '    }'
Ejemplo n.º 16
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.name in ('Map', 'Unmap'):
            # On D3D11 Map/Unmap is not a resource method, but a context method instead.
            resourceArg = method.getArgByName('pResource')
            if resourceArg is None:
                pResource = 'this'
            else:
                wrapperInterfaceName = getWrapperInterfaceName(
                    resourceArg.type.type)
                print '    %s * _pResource = static_cast<%s*>(%s);' % (
                    wrapperInterfaceName, wrapperInterfaceName,
                    resourceArg.name)
                pResource = '_pResource'

        if method.name == 'Unmap':
            print '    _MAP_DESC _MapDesc = %s->_MapDesc;' % pResource
            #print r'    os::log("%%p -> %%p+%%lu\n", %s,_MapDesc.pData, (unsigned long)_MapDesc.Size);' % pResource
            print '    if (_MapDesc.Size && _MapDesc.pData) {'
            self.emit_memcpy('_MapDesc.pData', '_MapDesc.Size')
            print '    }'

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base,
                                                      method)

        if method.name == 'Map':
            # NOTE: recursive locks are explicitely forbidden
            print '    _MAP_DESC _MapDesc;'
            print '    if (SUCCEEDED(_result)) {'
            print '        _getMapDesc(_this, %s, _MapDesc);' % ', '.join(
                method.argNames())
            print '    } else {'
            print '        _MapDesc.pData = NULL;'
            print '        _MapDesc.Size = 0;'
            print '    }'
            #print r'    os::log("%%p <- %%p+%%lu\n", %s,_MapDesc.pData, (unsigned long)_MapDesc.Size);' % pResource
            print '    %s->_MapDesc = _MapDesc;' % pResource
Ejemplo n.º 17
0
    def implementWrapperInterfaceMethodBody(self, interface, base, method):
        if method.getArgByName('pInitialData'):
            pDesc1 = method.getArgByName('pDesc1')
            if pDesc1 is not None:
                print(r'    %s pDesc = pDesc1;' % (pDesc1.type, ))

        if method.name in ('Map', 'Unmap'):
            # On D3D11 Map/Unmap is not a resource method, but a context method instead.
            resourceArg = method.getArgByName('pResource')
            if resourceArg is None:
                print('    _MAP_DESC & _MapDesc = m_MapDesc;')
                print('    MemoryShadow & _MapShadow = m_MapShadow;')
                print('    %s *pResourceInstance = m_pInstance;' %
                      interface.name)
            else:
                print(r'    static bool _warned = false;')
                print(
                    r'    if (_this->GetType() == D3D11_DEVICE_CONTEXT_DEFERRED && !_warned) {'
                )
                print(
                    r'        os::log("apitrace: warning: map with deferred context may not be realiably traced\n");'
                )
                print(r'        _warned = true;')
                print(r'    }')
                print(
                    '    _MAP_DESC & _MapDesc = m_MapDescs[std::pair<%s, UINT>(pResource, Subresource)];'
                    % resourceArg.type)
                print(
                    '    MemoryShadow & _MapShadow = m_MapShadows[std::pair<%s, UINT>(pResource, Subresource)];'
                    % resourceArg.type)
                print(
                    '    Wrap%spResourceInstance = static_cast<Wrap%s>(%s);' %
                    (resourceArg.type, resourceArg.type, resourceArg.name))

        if method.name == 'Unmap':
            print('    if (_MapDesc.Size && _MapDesc.pData) {')
            print('        if (_shouldShadowMap(pResourceInstance)) {')
            print('            _MapShadow.update(trace::fakeMemcpy);')
            print('        } else {')
            self.emit_memcpy('_MapDesc.pData', '_MapDesc.Size')
            print('        }')
            print('    }')

        if interface.hasBase(d3d11.ID3D11VideoContext) and \
           method.name == 'ReleaseDecoderBuffer':
            print(
                '    std::map<UINT, std::pair<void *, UINT> >::iterator it = m_MapDesc.find(Type);'
            )
            print('    if (it != m_MapDesc.end()) {')
            self.emit_memcpy('it->second.first', 'it->second.second')
            print('        m_MapDesc.erase(it);')
            print('    }')

        DllTracer.implementWrapperInterfaceMethodBody(self, interface, base,
                                                      method)

        if method.name == 'Map':
            # NOTE: recursive locks are explicitely forbidden
            print('    if (SUCCEEDED(_result)) {')
            print('        _getMapDesc(_this, %s, _MapDesc);' %
                  ', '.join(method.argNames()))
            print(
                '        if (_MapDesc.pData && _shouldShadowMap(pResourceInstance)) {'
            )
            if interface.name.startswith('IDXGI'):
                print('            (void)_MapShadow;')
            else:
                print(
                    '            bool _discard = MapType == 4 /* D3D1[01]_MAP_WRITE_DISCARD */;'
                )
                print(
                    '            _MapShadow.cover(_MapDesc.pData, _MapDesc.Size, _discard);'
                )
            print('        }')
            print('    } else {')
            print('        _MapDesc.pData = NULL;')
            print('        _MapDesc.Size = 0;')
            print('    }')

        if interface.hasBase(d3d11.ID3D11VideoContext) and \
           method.name == 'GetDecoderBuffer':
            print('    if (SUCCEEDED(_result)) {')
            print(
                '        m_MapDesc[Type] = std::make_pair(*ppBuffer, *pBufferSize);'
            )
            print('    } else {')
            print('        m_MapDesc[Type] = std::make_pair(nullptr, 0);')
            print('    }')