Ejemplo n.º 1
0
        private static Stream OpenResource(this SafeModuleHandle module, IntPtr resourceHandle)
        {
            IntPtr globalHandle = UnsafeNativeMethods.LoadResource(module, resourceHandle);

            if (globalHandle == IntPtr.Zero)
            {
                throw new IOException("Failed to load resource.", new Win32Exception());
            }

            long size = UnsafeNativeMethods.SizeofResource(module, resourceHandle);

            if (size == 0)
            {
                throw new IOException("Unable to retrieve resource size.", new Win32Exception());
            }

            IntPtr data = UnsafeNativeMethods.LockResource(globalHandle);

            if (data == IntPtr.Zero)
            {
                throw new IOException("Failed to lock resource.", new Win32Exception());
            }

            var resource = new SafeResourceBuffer(data, size);

            return(new UnmanagedMemoryStream(resource, 0, size));
        }
Ejemplo n.º 2
0
        private static SafeResourceBuffer GetResourceBuffer(HandleRef hModule, UIntPtr lpName, UIntPtr lpType)
        {
            IntPtr hresinfo = FindResource(hModule, lpName, lpType);

            if (hresinfo == IntPtr.Zero)
            {
                int error = Marshal.GetLastWin32Error();
                if (error >= ERROR_RESOURCE_DATA_NOT_FOUND && error <= ERROR_RESOURCE_LANG_NOT_FOUND)
                {
                    Win32Exception ex = new Win32Exception(error);
                    throw new KeyNotFoundException(ex.Message, ex);
                }
                throw new Win32Exception(error);
            }
            uint size = SizeofResource(hModule, hresinfo);

            if (size == 0)
            {
                throw new Win32Exception();
            }
            IntPtr hresdata = LoadResource(hModule, hresinfo);

            if (hresdata == IntPtr.Zero)
            {
                throw new Win32Exception();
            }

            SafeResourceBuffer result = LockResource(hresdata);

            if (result == null || result.IsInvalid)
            {
                throw new OutOfMemoryException();
            }
            result.Initialize(size);
            return(result);
        }
Ejemplo n.º 3
0
        private static Icon LoadIconFromResource(UIntPtr lpIconName)
        {
            HandleRef hmodule = new HandleRef(null, GetModuleHandle(null));

            uint totalsize;

            RESOURCE_ICONDIRENTRY[] entries;
            SafeResourceBuffer[]    entrybuffers;
            RESOURCE_ICONDIR        dir;

            using (SafeResourceBuffer buffer = GetResourceBuffer(hmodule, lpIconName, MAKEINTRESOURCE(RT_GROUP_ICON)))
            {
                dir = buffer.Read <RESOURCE_ICONDIR>(0);
                if (dir.idReserved != 0 || dir.idType != IMAGE_ICON || dir.idCount == 0)
                {
                    throw new InvalidDataException("There is no icon directory in resource data.");
                }

                entries      = new RESOURCE_ICONDIRENTRY[dir.idCount];
                entrybuffers = new SafeResourceBuffer[dir.idCount];
                uint  entrysize = (uint)Marshal.SizeOf(typeof(RESOURCE_ICONDIRENTRY));
                ulong offset    = (uint)Marshal.SizeOf(typeof(RESOURCE_ICONDIR)) - entrysize;
                totalsize = (uint)(Marshal.SizeOf(typeof(ICONDIR)) + (Marshal.SizeOf(typeof(ICONDIRENTRY)) * (dir.idCount - 1)));

                entries[0] = dir.idEntries;
                for (int i = 0; i < dir.idCount; i++, offset += entrysize)
                {
                    if (i > 0)
                    {
                        entries[i] = buffer.Read <RESOURCE_ICONDIRENTRY>(offset);
                    }

                    uint iconsize = entries[i].dwBytesInRes;
                    SafeResourceBuffer entrybuffer = GetResourceBuffer(hmodule, MAKEINTRESOURCE(entries[i].nID), MAKEINTRESOURCE(RT_ICON));
                    if (iconsize != entrybuffer.ByteLength)
                    {
                        throw new InvalidDataException("Reported resource size is not equal to the icon size.");
                    }

                    entrybuffers[i] = entrybuffer;
                    totalsize      += iconsize;
                }
            }

            using (SafeLocalAllocHandle iconbuffer = SafeLocalAlloc(LMEM_ZEROINIT | LMEM_FIXED, totalsize))
            {
                using (UnmanagedMemoryStream outstream = iconbuffer.ToStream(FileAccess.ReadWrite))
                {
                    ICONDIR icondir = new ICONDIR(dir);
                    iconbuffer.Write(0, icondir);

                    uint iconoffset = icondir.idEntries.dwImageOffset;
                    outstream.Position = iconoffset;
                    uint         entrysize = (uint)Marshal.SizeOf(typeof(ICONDIRENTRY));
                    ulong        offset    = (uint)Marshal.SizeOf(typeof(ICONDIR));
                    ICONDIRENTRY entry     = icondir.idEntries;
                    for (int i = 0; i < dir.idCount; i++, offset += entrysize)
                    {
                        if (i > 0)
                        {
                            entry = new ICONDIRENTRY(entries[i], iconoffset);
                            iconbuffer.Write(offset, entry);
                        }

                        using (UnmanagedMemoryStream instream = entrybuffers[i].ToStream())
                        {
                            instream.CopyTo(outstream);
                        }

                        if (outstream.Position != (iconoffset + entry.dwBytesInRes))
                        {
                            throw new InvalidOperationException();
                        }

                        iconoffset += entry.dwBytesInRes;
                    }

                    outstream.Position = 0;
                    return(new Icon(outstream));
                }
            }
        }