2 Copyright © 1995-2007, The AROS Development Team. All rights reserved.
5 Desc: Graphics function GetDisplayInfoData()
8 #include <aros/debug.h>
9 #include <proto/graphics.h>
10 #include <graphics/displayinfo.h>
11 #include <hidd/graphics.h>
13 #include <proto/oop.h>
16 #include "graphics_intern.h"
18 /****************************************************************************************/
27 #define PRIV_DTAG_QHDR 0x80005000
29 static const struct size_check size_checks
[] =
31 { DTAG_DISP
, sizeof(struct DisplayInfo
), "DisplayInfo" },
32 { DTAG_DIMS
, sizeof(struct DimensionInfo
), "DimensionInfo" },
33 { DTAG_MNTR
, sizeof(struct MonitorInfo
), "MonitorInfo" },
34 { DTAG_NAME
, sizeof(struct NameInfo
), "NameInfo" },
35 { DTAG_VEC
, sizeof(struct VecInfo
), "VecInfo" },
36 { PRIV_DTAG_QHDR
, sizeof(struct QueryHeader
), "QueryHeader" }
40 static BOOL
check_sizes(ULONG tagID
, ULONG size
);
41 static ULONG
compute_numbits(HIDDT_Pixel mask
);
43 #define DLONGSZ (sizeof (ULONG) * 2)
44 #define DTAG_TO_IDX(dtag) (((dtag) & 0x0000F000) >> 12)
46 /*****************************************************************************
49 #include <proto/graphics.h>
51 AROS_LH5(ULONG
, GetDisplayInfoData
,
54 AROS_LHA(DisplayInfoHandle
, handle
, A0
),
55 AROS_LHA(UBYTE
*, buf
, A1
),
56 AROS_LHA(ULONG
, size
, D0
),
57 AROS_LHA(ULONG
, tagID
, D1
),
58 AROS_LHA(ULONG
, ID
, D2
),
61 struct GfxBase
*, GfxBase
, 126, Graphics
)
64 Fills buffer with information about displayinfo handle.
67 handle - displayinfo handle
68 buf - pointer to destination buffer
69 size - buffer size in bytes
70 tagID - data chunk type
71 DTAG_DISP (DisplayInfo)
72 DTAG_DIMS (DimensionInfo)
73 DTAG_MNTR (MonitorInfo)
75 ID - displayinfo identifier, optionally used if handle is NULL
78 result - if positive, number of bytes actually transferred
79 if zero, no information for ID was available
88 FindDisplayInfo(), NextDisplayInfo(), graphics/displayinfo.h
95 ******************************************************************************/
99 struct QueryHeader
*qh
;
101 OOP_Object
*sync
, *pf
;
102 HIDDT_ModeID hiddmode
;
107 if ((ULONG
)INVALID_ID
!= ID
)
109 /* Check that ID is a valid modeid */
110 handle
= FindDisplayInfo(ID
);
114 D(bug("!!! INVALID MODE ID IN GetDisplayInfoData()\n"));
121 D(bug("!!! COULD NOT GET HANDLE IN GetDisplayInfoData()\n"));
125 modeid
= (ULONG
)handle
;
126 hiddmode
= (HIDDT_ModeID
)AMIGA_TO_HIDD_MODEID(modeid
);
128 /* Get mode info from the HIDD */
129 if (!HIDD_Gfx_GetMode(SDD(GfxBase
)->gfxhidd
, hiddmode
, &sync
, &pf
))
131 D(bug("NO VALID MODE PASSED TO GetDisplayInfoData() !!!\n"));
136 D(bug("GetDisplayInfoData(handle=%d, modeid=%x, tagID=%x)\n"
137 , (ULONG
)handle
, modeid
, tagID
));
140 /* Build the queryheader */
141 if (!check_sizes(tagID
, size
)) return 0;
143 memset(buf
, 0, size
);
145 /* Fill in the queryheader */
146 qh
= (struct QueryHeader
*)buf
;
147 qh
->StructID
= tagID
;
148 qh
->DisplayID
= modeid
;
149 qh
->SkipID
= TAG_SKIP
;
151 structsize
= size_checks
[DTAG_TO_IDX(tagID
)].struct_size
;
152 qh
->Length
= (structsize
+ (DLONGSZ
- 1)) / DLONGSZ
;
158 struct DisplayInfo
*di
;
159 IPTR redmask
, greenmask
, bluemask
;
161 di
= (struct DisplayInfo
*)buf
;
163 /* All modes returned from the HIDD are available */
164 di
->NotAvailable
= FALSE
;
166 /* Set the propertyflags */
167 di
->PropertyFlags
= DIPF_IS_FOREIGN
| DIPF_IS_WB
;
169 /* We simulate AGA. This field is really obsolete */
170 di
->PaletteRange
= 4096;
172 /* Compute red green and blue bits */
173 OOP_GetAttr(pf
, aHidd_PixFmt_RedMask
, &redmask
);
174 OOP_GetAttr(pf
, aHidd_PixFmt_GreenMask
, &greenmask
);
175 OOP_GetAttr(pf
, aHidd_PixFmt_BlueMask
, &bluemask
);
177 di
->RedBits
= compute_numbits(redmask
);
178 di
->GreenBits
= compute_numbits(greenmask
);
179 di
->BlueBits
= compute_numbits(bluemask
);
181 di
->Resolution
.x
= 22;
182 di
->Resolution
.y
= 22;
185 di->Resolution.x = ?;
186 di->Resolution.y = ?;
188 di->NumStdSprites = ?
189 di->SpriteResolution.x = ?;
190 di->SpriteResolution.y = ?;
198 struct DimensionInfo
*di
;
199 IPTR depth
, width
, height
;
201 OOP_GetAttr(pf
, aHidd_PixFmt_Depth
, &depth
);
202 OOP_GetAttr(sync
, aHidd_Sync_HDisp
, &width
);
203 OOP_GetAttr(sync
, aHidd_Sync_VDisp
, &height
);
205 di
= (struct DimensionInfo
*)buf
;
206 di
->MaxDepth
= depth
;
208 di
->MinRasterWidth
= width
;
209 di
->MinRasterHeight
= height
;
210 di
->MaxRasterWidth
= width
;
211 di
->MaxRasterHeight
= height
;
213 di
->Nominal
.MinX
= 0;
214 di
->Nominal
.MinY
= 0;
215 di
->Nominal
.MaxX
= width
- 1;
216 di
->Nominal
.MaxY
= height
- 1;
219 #warning What about the OSCAN stuff ??
220 di
->MaxOScan
= di
->Nominal
;
221 di
->VideoOScan
= di
->Nominal
;
222 di
->TxtOScan
= di
->Nominal
;
223 di
->StdOScan
= di
->Nominal
;
226 di->MaxOScan.MinX = di->Nominal.MinX;
227 di->MaxOScan.MinY = di->Nominal.MinY;
228 di->MaxOScan.MaxX = di->Nominal.MaxX;
229 di->MaxOScan.MaxY = di->Nominal.MaxY;
232 di->VideoOScan.MinX = di->Nominal.MinX;
233 di->VideoOScan.MinY = di->Nominal.MinY;
234 di->VideoOScan.MaxX = di->Nominal.MaxX;
235 di->VideoOScan.MaxY = di->Nominal.MaxY;
237 di->TxtOScan.MinX = di->Nominal.MinX;
238 di->TxtOScan.MinY = di->Nominal.MinY;
239 di->TxtOScan.MaxX = di->Nominal.MaxX;
240 di->TxtOScan.MaxY = di->Nominal.MaxY;
242 di->StdOScan.MinX = di->Nominal.MinX;
243 di->StdOScan.MinY = di->Nominal.MinY;
244 di->StdOScan.MaxX = di->Nominal.MaxX;
245 di->StdOScan.MaxY = di->Nominal.MaxY;
252 struct MonitorInfo
*mi
;
253 struct MonitorSpec
*mspc
;
254 struct displayinfo_db
*db
;
257 db
= (struct displayinfo_db
*)SDD(GfxBase
)->dispinfo_db
;
259 ObtainSemaphoreShared(&db
->sema
);
260 majoridx
= MAJORID2NUM(modeid
);
261 if (majoridx
>= db
->num_mspecs
)
263 D(bug("!!! INVALID MODE ID IN GetDisplayInfoData(DTAG_MNTR) !!!\n"));
264 ReleaseSemaphore(&db
->sema
);
269 mi
= (struct MonitorInfo
*)buf
;
271 mspc
= &db
->mspecs
[majoridx
];
274 mi->ViewPosition.X = ?;
275 mi->ViewPosition.Y = ?;
276 mi->ViewResolution.X = ?;
277 mi->ViewResolution.Y = ?;
278 mi->ViewPositionRange.MinX = ?;
279 mi->ViewPositionRange.MinY = ?;
280 mi->ViewPositionRange.MaxX = ?;
281 mi->ViewPositionRange.MaxY = ?;
283 mi->TotalColorClocks = ?;
285 mi->MouseTicks.X = ?;
286 mi->MouseTicks.Y = ?;
287 mi->DefaultViewPosition.X = ?;
288 mi->DefaultViewPosition.Y = ?;
293 mi
->PreferredModeID
= modeid
;
294 mi
->Compatibility
= MCOMPAT_NOBODY
;
296 /* Fill info into the monitorspec. It is by default set to all 0s */
297 mspc
->ms_Node
.xln_Pred
= mspc
->ms_Node
.xln_Succ
= NULL
;
298 mspc
->ms_Node
.xln_Type
= MONITOR_SPEC_TYPE
;
299 mspc
->ms_Node
.xln_Name
= "AROS.monitor";
300 mspc
->total_rows
= mi
->TotalRows
;
301 mspc
->total_colorclocks
= mi
->TotalColorClocks
;
302 mspc
->min_row
= mi
->MinRow
;
304 /* What to put in here ? */
306 ReleaseSemaphore(&db
->sema
);
313 IPTR depth
, width
, height
, stdpixfmt
;
314 STRPTR sync_description
;
316 OOP_GetAttr(pf
, aHidd_PixFmt_Depth
, &depth
);
317 OOP_GetAttr(pf
, aHidd_PixFmt_StdPixFmt
, &stdpixfmt
);
319 OOP_GetAttr(sync
, aHidd_Sync_HDisp
, &width
);
320 OOP_GetAttr(sync
, aHidd_Sync_VDisp
, &height
);
321 OOP_GetAttr(sync
, aHidd_Sync_Description
, (IPTR
*)&sync_description
);
322 ni
= (struct NameInfo
*)buf
;
324 if (sync_description
&& sync_description
[0] &&
325 (IS_REAL_STDPIXFMT(stdpixfmt
) || (stdpixfmt
== vHidd_StdPixFmt_Unknown
)))
327 STRPTR pixfmt_name
= "";
331 case vHidd_StdPixFmt_RGB16
:
332 case vHidd_StdPixFmt_RGB15
:
333 case vHidd_StdPixFmt_RGB24
:
337 case vHidd_StdPixFmt_RGB16_LE
:
338 case vHidd_StdPixFmt_RGB15_LE
:
339 pixfmt_name
= "RGB PC";
342 case vHidd_StdPixFmt_BGR24
:
343 case vHidd_StdPixFmt_BGR16
:
344 case vHidd_StdPixFmt_BGR15
:
348 case vHidd_StdPixFmt_BGR16_LE
:
349 case vHidd_StdPixFmt_BGR15_LE
:
350 pixfmt_name
= "BGR PC";
353 case vHidd_StdPixFmt_ARGB32
:
354 pixfmt_name
= "ARGB";
357 case vHidd_StdPixFmt_BGRA32
:
358 pixfmt_name
= "BGRA";
361 case vHidd_StdPixFmt_RGBA32
:
362 pixfmt_name
= "RGBA";
365 case vHidd_StdPixFmt_0RGB32
:
366 pixfmt_name
= "0RGB";
369 case vHidd_StdPixFmt_BGR032
:
370 pixfmt_name
= "BGR0";
373 case vHidd_StdPixFmt_RGB032
:
374 pixfmt_name
= "RGB0";
379 snprintf(ni
->Name
, DISPLAYNAMELEN
, "%s %2dbit %s",
380 sync_description
, (int)depth
, pixfmt_name
);
384 snprintf(ni
->Name
, DISPLAYNAMELEN
, "AROS: %ldx%ldx%ld", width
, height
, depth
);
390 D(bug("!!! UNKNOWN tagID IN CALL TO GetDisplayInfoData() !!!\n"));
395 D(bug("GDID: %d\n", structsize
));
401 } /* GetDisplayInfoData */
403 /****************************************************************************************/
405 static BOOL
check_sizes(ULONG tagID
, ULONG size
)
408 const struct size_check
*sc
;
410 idx
= DTAG_TO_IDX(tagID
);
414 D(bug("!!! INVALID tagID TO GetDisplayInfoData"));
418 sc
= &size_checks
[idx
];
419 if (sc
->struct_id
!= tagID
)
421 D(bug("!!! INVALID tagID TO GetDisplayInfoData"));
425 if (sc
->struct_size
> size
)
427 D(bug("!!! NO SPACE FOR %s IN BUFFER SUPPLIED TO GetDisplayInfoData !!!\n"
435 /****************************************************************************************/
437 static ULONG
compute_numbits(HIDDT_Pixel mask
)
442 for (i
= 0; i
<= 31; i
++)
444 if (mask
& (1L << i
)) numbits
++;
450 /****************************************************************************************/
453 /****************************************************************************************/