4 ISA-PnP -- A Plug And Play ISA software layer for AmigaOS.
5 Copyright (C) 2001 Martin Blom <martin@blom.org>
6 Copyright (C) 2009-2013 The AROS Development Team
8 This library is free software; you can redistribute it and/or
9 modify it under the terms of the GNU Library General Public
10 License as published by the Free Software Foundation; either
11 version 2 of the License, or (at your option) any later version.
13 This library is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 Library General Public License for more details.
18 You should have received a copy of the GNU Library General Public
19 License along with this library; if not, write to the
20 Free Software Foundation, Inc., 59 Temple Place - Suite 330, Cambridge,
24 #include "CompilerSpecific.h"
26 #include <exec/memory.h>
28 #include <proto/exec.h>
32 #include <resources/isapnp.h>
33 #include "isapnp_private.h"
36 /******************************************************************************
37 ** Find a PNP ISA card *******************************************************
38 ******************************************************************************/
40 AROS_LH5(struct ISAPNP_Card
*, ISAPNP_FindCard
,
41 AROS_LHA(struct ISAPNP_Card
*, last_card
, A0
),
42 AROS_LHA(LONG
, manufacturer
, D0
),
43 AROS_LHA(WORD
, product
, D1
),
44 AROS_LHA(BYTE
, revision
, D2
),
45 AROS_LHA(LONG
, serial
, D3
),
46 struct ISAPNPBase
*, res
, 28, ISAPNP
)
50 struct ISAPNP_Card
* card
;
52 if( last_card
== NULL
)
54 card
= (struct ISAPNP_Card
*) res
->m_Cards
.lh_Head
;
58 card
= (struct ISAPNP_Card
*) last_card
->isapnpc_Node
.ln_Succ
;
61 while( card
->isapnpc_Node
.ln_Succ
!= NULL
)
63 if( manufacturer
== -1 ||
64 ISAPNP_MAKE_ID( card
->isapnpc_ID
.isapnpid_Vendor
[ 0 ],
65 card
->isapnpc_ID
.isapnpid_Vendor
[ 1 ],
66 card
->isapnpc_ID
.isapnpid_Vendor
[ 2 ] ) == manufacturer
)
68 if( product
== -1 || card
->isapnpc_ID
.isapnpid_ProductID
== product
)
70 if( revision
== -1 || card
->isapnpc_ID
.isapnpid_Revision
== revision
)
72 if( serial
== -1 || (LONG
) card
->isapnpc_SerialNumber
== serial
)
80 card
= (struct ISAPNP_Card
*) card
->isapnpc_Node
.ln_Succ
;
89 /******************************************************************************
90 ** Find a PNP ISA device *****************************************************
91 ******************************************************************************/
93 AROS_LH4(struct ISAPNP_Device
*, ISAPNP_FindDevice
,
94 AROS_LHA(struct ISAPNP_Device
*, last_device
, A0
),
95 AROS_LHA(LONG
, manufacturer
, D0
),
96 AROS_LHA(WORD
, product
, D1
),
97 AROS_LHA(BYTE
, revision
, D2
),
98 struct ISAPNPBase
*, res
, 29, ISAPNP
)
102 struct ISAPNP_Card
* card
;
103 struct ISAPNP_Device
* dev
;
105 if( last_device
== NULL
)
107 card
= (struct ISAPNP_Card
*) res
->m_Cards
.lh_Head
;
108 dev
= (struct ISAPNP_Device
*) card
->isapnpc_Devices
.lh_Head
;
112 card
= (struct ISAPNP_Card
*) last_device
->isapnpd_Card
;
113 dev
= (struct ISAPNP_Device
*) last_device
->isapnpd_Node
.ln_Succ
;
116 while( card
->isapnpc_Node
.ln_Succ
!= NULL
)
118 while( dev
->isapnpd_Node
.ln_Succ
!= NULL
)
120 struct ISAPNP_Identifier
* id
;
122 for( id
= (struct ISAPNP_Identifier
*) dev
->isapnpd_IDs
.mlh_Head
;
123 id
->isapnpid_MinNode
.mln_Succ
!= NULL
;
124 id
= (struct ISAPNP_Identifier
*) id
->isapnpid_MinNode
.mln_Succ
)
126 if( manufacturer
== -1 ||
127 ISAPNP_MAKE_ID( id
->isapnpid_Vendor
[ 0 ],
128 id
->isapnpid_Vendor
[ 1 ],
129 id
->isapnpid_Vendor
[ 2 ] ) == manufacturer
)
131 if( product
== -1 || id
->isapnpid_ProductID
== product
)
133 if( revision
== -1 || id
->isapnpid_Revision
== revision
)
141 dev
= (struct ISAPNP_Device
*) dev
->isapnpd_Node
.ln_Succ
;
144 card
= (struct ISAPNP_Card
*) card
->isapnpc_Node
.ln_Succ
;
145 dev
= (struct ISAPNP_Device
*) card
->isapnpc_Devices
.lh_Head
;
155 /******************************************************************************
156 ** Helper functions for the card/device locking functions *********************
157 ******************************************************************************/
160 ComparePtr( const void* a
,
163 struct ISAPNP_Card
* p1
= *( (struct ISAPNP_Card
**) a
);
164 struct ISAPNP_Card
* p2
= *( (struct ISAPNP_Card
**) b
);
171 MakeSortedArray( void** ptrs
, struct ISAPNPBase
*res
)
177 // Find number of pointers to sort
182 while( *ptrs_ptr
!= NULL
)
188 result
= AllocVec( sizeof( *ptrs_ptr
) * size
+ 1, MEMF_PUBLIC
);
194 while( *ptrs
!= NULL
)
201 qsort( result
, size
, sizeof( *result
), ComparePtr
);
203 result
[ size
] = NULL
;
210 /******************************************************************************
211 ** Lock one or more PNP ISA cards ********************************************
212 ******************************************************************************/
214 AROS_LH2(APTR
, ISAPNP_LockCardsA
,
215 AROS_LHA(ULONG
, flags
, D0
),
216 AROS_LHA(struct ISAPNP_Card
**, cards
, A0
),
217 struct ISAPNPBase
*, res
, 30, ISAPNP
)
221 struct ISAPNP_Card
** cards_ptr
;
222 struct ISAPNP_Card
** result
;
224 result
= (struct ISAPNP_Card
**) MakeSortedArray( (void**) cards
, res
);
228 for( cards_ptr
= result
;
232 if( flags
& ISAPNP_LOCKF_NONBLOCKING
)
234 if( ! AttemptSemaphore( &(*cards_ptr
)->isapnpc_Lock
) )
236 struct ISAPNP_Card
** cards_end
;
238 // Oops! Failed to lock one of the cards!
240 cards_end
= cards_ptr
;
242 for( cards_ptr
= result
;
243 cards_ptr
!= cards_end
;
246 ReleaseSemaphore( &(*cards_ptr
)->isapnpc_Lock
);
256 ObtainSemaphore( &(*cards_ptr
)->isapnpc_Lock
);
261 return (APTR
) result
;
267 /******************************************************************************
268 ** Unlock one or more PNP ISA cards ******************************************
269 ******************************************************************************/
271 AROS_LH1(void, ISAPNP_UnlockCards
,
272 AROS_LHA(APTR
, card_lock_handle
, A0
),
273 struct ISAPNPBase
*, res
, 31, ISAPNP
)
277 struct ISAPNP_Card
** cards_ptr
;
279 if( card_lock_handle
== NULL
)
284 for( cards_ptr
= (struct ISAPNP_Card
**) card_lock_handle
;
288 ReleaseSemaphore( &(*cards_ptr
)->isapnpc_Lock
);
291 FreeVec( card_lock_handle
);
297 /******************************************************************************
298 ** Lock one or more PNP ISA devices *******************************************
299 ******************************************************************************/
301 AROS_LH2(APTR
, ISAPNP_LockDevicesA
,
302 AROS_LHA(ULONG
, flags
, D0
),
303 AROS_LHA(struct ISAPNP_Device
**, devices
, A0
),
304 struct ISAPNPBase
*, res
, 32, ISAPNP
)
308 struct ISAPNP_Device
** devices_ptr
;
309 struct ISAPNP_Device
** result
;
311 result
= (struct ISAPNP_Device
**) MakeSortedArray( (void**) devices
, res
);
315 for( devices_ptr
= result
;
316 *devices_ptr
!= NULL
;
319 if( flags
& ISAPNP_LOCKF_NONBLOCKING
)
321 if( ! AttemptSemaphore( &(*devices_ptr
)->isapnpd_Lock
) )
323 struct ISAPNP_Device
** devices_end
;
325 // Oops! Failed to lock one of the devices!
327 devices_end
= devices_ptr
;
329 for( devices_ptr
= result
;
330 devices_ptr
!= devices_end
;
333 ReleaseSemaphore( &(*devices_ptr
)->isapnpd_Lock
);
343 ObtainSemaphore( &(*devices_ptr
)->isapnpd_Lock
);
348 return (APTR
) result
;
354 /******************************************************************************
355 ** Unlock one or more PNP ISA devices ****************************************
356 ******************************************************************************/
358 AROS_LH1(void, ISAPNP_UnlockDevices
,
359 AROS_LHA(APTR
, device_lock_handle
, A0
),
360 struct ISAPNPBase
*, res
, 33, ISAPNP
)
364 struct ISAPNP_Device
** devices_ptr
;
366 if( device_lock_handle
== NULL
)
371 for( devices_ptr
= (struct ISAPNP_Device
**) device_lock_handle
;
372 *devices_ptr
!= NULL
;
375 ReleaseSemaphore( &(*devices_ptr
)->isapnpd_Lock
);
378 FreeVec( device_lock_handle
);