2 * MSCMS - Color Management System for Wine
4 * Copyright 2004, 2005, 2008 Hans Leidekker
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
22 #include "wine/debug.h"
32 #include "mscms_priv.h"
36 static CRITICAL_SECTION MSCMS_handle_cs
;
37 static CRITICAL_SECTION_DEBUG MSCMS_handle_cs_debug
=
39 0, 0, &MSCMS_handle_cs
,
40 { &MSCMS_handle_cs_debug
.ProcessLocksList
,
41 &MSCMS_handle_cs_debug
.ProcessLocksList
},
42 0, 0, { (DWORD_PTR
)(__FILE__
": MSCMS_handle_cs") }
44 static CRITICAL_SECTION MSCMS_handle_cs
= { &MSCMS_handle_cs_debug
, -1, 0, 0, 0, 0 };
46 static struct profile
*profiletable
;
47 static struct transform
*transformtable
;
49 static unsigned int num_profile_handles
;
50 static unsigned int num_transform_handles
;
52 WINE_DEFAULT_DEBUG_CHANNEL(mscms
);
54 void free_handle_tables( void )
56 HeapFree( GetProcessHeap(), 0, profiletable
);
58 num_profile_handles
= 0;
60 HeapFree( GetProcessHeap(), 0, transformtable
);
61 transformtable
= NULL
;
62 num_transform_handles
= 0;
64 DeleteCriticalSection( &MSCMS_handle_cs
);
67 struct profile
*grab_profile( HPROFILE handle
)
71 EnterCriticalSection( &MSCMS_handle_cs
);
73 index
= (DWORD_PTR
)handle
- 1;
74 if (index
> num_profile_handles
)
76 LeaveCriticalSection( &MSCMS_handle_cs
);
79 return &profiletable
[index
];
82 void release_profile( struct profile
*profile
)
84 LeaveCriticalSection( &MSCMS_handle_cs
);
87 struct transform
*grab_transform( HTRANSFORM handle
)
91 EnterCriticalSection( &MSCMS_handle_cs
);
93 index
= (DWORD_PTR
)handle
- 1;
94 if (index
> num_transform_handles
)
96 LeaveCriticalSection( &MSCMS_handle_cs
);
99 return &transformtable
[index
];
102 void release_transform( struct transform
*transform
)
104 LeaveCriticalSection( &MSCMS_handle_cs
);
107 static HPROFILE
alloc_profile_handle( void )
111 unsigned int count
= 128;
113 for (index
= 0; index
< num_profile_handles
; index
++)
115 if (!profiletable
[index
].iccprofile
) return (HPROFILE
)(index
+ 1);
119 p
= HeapAlloc( GetProcessHeap(), HEAP_ZERO_MEMORY
, count
* sizeof(struct profile
) );
123 count
= num_profile_handles
* 2;
124 p
= HeapReAlloc( GetProcessHeap(), HEAP_ZERO_MEMORY
, profiletable
, count
* sizeof(struct profile
) );
129 num_profile_handles
= count
;
131 return (HPROFILE
)(index
+ 1);
134 HPROFILE
create_profile( struct profile
*profile
)
138 EnterCriticalSection( &MSCMS_handle_cs
);
140 if ((handle
= alloc_profile_handle()))
142 DWORD_PTR index
= (DWORD_PTR
)handle
- 1;
143 memcpy( &profiletable
[index
], profile
, sizeof(struct profile
) );
145 LeaveCriticalSection( &MSCMS_handle_cs
);
149 BOOL
close_profile( HPROFILE handle
)
152 struct profile
*profile
;
154 EnterCriticalSection( &MSCMS_handle_cs
);
156 index
= (DWORD_PTR
)handle
- 1;
157 if (index
> num_profile_handles
)
159 LeaveCriticalSection( &MSCMS_handle_cs
);
162 profile
= &profiletable
[index
];
164 if (profile
->file
!= INVALID_HANDLE_VALUE
)
166 if (profile
->access
& PROFILE_READWRITE
)
168 DWORD written
, size
= MSCMS_get_profile_size( profile
->iccprofile
);
170 if (SetFilePointer( profile
->file
, 0, NULL
, FILE_BEGIN
) ||
171 !WriteFile( profile
->file
, profile
->iccprofile
, size
, &written
, NULL
) ||
174 ERR( "Unable to write color profile\n" );
177 CloseHandle( profile
->file
);
179 cmsCloseProfile( profile
->cmsprofile
);
180 HeapFree( GetProcessHeap(), 0, profile
->iccprofile
);
182 memset( profile
, 0, sizeof(struct profile
) );
184 LeaveCriticalSection( &MSCMS_handle_cs
);
188 static HTRANSFORM
alloc_transform_handle( void )
192 unsigned int count
= 128;
194 for (index
= 0; index
< num_transform_handles
; index
++)
196 if (!transformtable
[index
].cmstransform
) return (HTRANSFORM
)(index
+ 1);
200 p
= HeapAlloc( GetProcessHeap(), HEAP_ZERO_MEMORY
, count
* sizeof(struct transform
) );
204 count
= num_transform_handles
* 2;
205 p
= HeapReAlloc( GetProcessHeap(), HEAP_ZERO_MEMORY
, transformtable
, count
* sizeof(struct transform
) );
210 num_transform_handles
= count
;
212 return (HTRANSFORM
)(index
+ 1);
215 HTRANSFORM
create_transform( struct transform
*transform
)
219 EnterCriticalSection( &MSCMS_handle_cs
);
221 if ((handle
= alloc_transform_handle()))
223 DWORD_PTR index
= (DWORD_PTR
)handle
- 1;
224 memcpy( &transformtable
[index
], transform
, sizeof(struct transform
) );
226 LeaveCriticalSection( &MSCMS_handle_cs
);
230 BOOL
close_transform( HTRANSFORM handle
)
233 struct transform
*transform
;
235 EnterCriticalSection( &MSCMS_handle_cs
);
237 index
= (DWORD_PTR
)handle
- 1;
238 if (index
> num_transform_handles
)
240 LeaveCriticalSection( &MSCMS_handle_cs
);
243 transform
= &transformtable
[index
];
245 cmsDeleteTransform( transform
->cmstransform
);
246 memset( transform
, 0, sizeof(struct transform
) );
248 LeaveCriticalSection( &MSCMS_handle_cs
);
252 #endif /* HAVE_LCMS */