2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS Kernel Streaming
4 * FILE: drivers/ksfilter/ks/topoology.c
5 * PURPOSE: KS Allocator functions
6 * PROGRAMMER: Johannes Anderwald
16 IN HANDLE ParentHandle
,
18 PVOID CreateParameters
,
19 UINT CreateParametersSize
,
20 IN ACCESS_MASK DesiredAccess
,
21 OUT PHANDLE NodeHandle
)
24 IO_STATUS_BLOCK IoStatusBlock
;
25 OBJECT_ATTRIBUTES ObjectAttributes
;
28 /* calculate request length */
30 Name
.MaximumLength
= wcslen(ObjectType
) * sizeof(WCHAR
) + CreateParametersSize
+ 1 * sizeof(WCHAR
);
31 Name
.MaximumLength
+= sizeof(WCHAR
);
32 /* acquire request buffer */
33 Name
.Buffer
= AllocateItem(NonPagedPool
, Name
.MaximumLength
);
34 /* check for success */
37 /* insufficient resources */
38 return STATUS_INSUFFICIENT_RESOURCES
;
41 /* build a request which looks like {ObjectClass}\CreateParameters
42 * For pins the parent is the reference string used in registration
43 * For clocks it is full path for pin\{ClockGuid}\ClockCreateParams
45 RtlAppendUnicodeToString(&Name
, ObjectType
);
46 RtlAppendUnicodeToString(&Name
, L
"\\");
47 /* append create parameters */
48 RtlMoveMemory(Name
.Buffer
+ (Name
.Length
/ sizeof(WCHAR
)), CreateParameters
, CreateParametersSize
);
49 Name
.Length
+= CreateParametersSize
;
50 Name
.Buffer
[Name
.Length
/ 2] = L
'\0';
52 InitializeObjectAttributes(&ObjectAttributes
, &Name
, OBJ_KERNEL_HANDLE
| OBJ_CASE_INSENSITIVE
| OBJ_OPENIF
, ParentHandle
, NULL
);
53 /* create the instance */
54 Status
= IoCreateFile(NodeHandle
,
67 IO_NO_PARAMETER_CHECKING
| IO_FORCE_ACCESS_CHECK
);
69 /* free request buffer */
70 FreeItem(Name
.Buffer
);
78 KSDDKAPI NTSTATUS NTAPI
80 IN HANDLE ParentHandle
,
81 IN PKSNODE_CREATE NodeCreate
,
82 IN ACCESS_MASK DesiredAccess
,
83 OUT PHANDLE NodeHandle
)
85 return KspCreateObjectType(ParentHandle
,
86 KSSTRING_TopologyNode
,
88 sizeof(KSNODE_CREATE
),
99 KsValidateTopologyNodeCreateRequest(
101 IN PKSTOPOLOGY Topology
,
102 OUT PKSNODE_CREATE
* OutNodeCreate
)
104 PKSNODE_CREATE NodeCreate
;
108 /* did the caller miss the topology */
110 return STATUS_INVALID_PARAMETER
;
112 /* set create param size */
113 Size
= sizeof(KSNODE_CREATE
);
115 /* fetch create parameters */
116 Status
= KspCopyCreateRequest(Irp
,
117 KSSTRING_TopologyNode
,
119 (PVOID
*)&NodeCreate
);
121 if (!NT_SUCCESS(Status
))
124 if (NodeCreate
->CreateFlags
!= 0 || (NodeCreate
->Node
>= Topology
->TopologyNodesCount
&& NodeCreate
->Node
!= MAXULONG
))
126 /* invalid node create */
127 FreeItem(NodeCreate
);
128 return STATUS_UNSUCCESSFUL
;
132 *OutNodeCreate
= NodeCreate
;
143 KsTopologyPropertyHandler(
145 IN PKSPROPERTY Property
,
147 IN
const KSTOPOLOGY
* Topology
)
150 PIO_STACK_LOCATION IoStack
;
152 PKEY_VALUE_PARTIAL_INFORMATION KeyInfo
;
155 IoStack
= IoGetCurrentIrpStackLocation(Irp
);
157 DPRINT("KsTopologyPropertyHandler Irp %p Property %p Data %p Topology %p OutputLength %lu PropertyId %lu\n", Irp
, Property
, Data
, Topology
, IoStack
->Parameters
.DeviceIoControl
.OutputBufferLength
, Property
->Id
);
159 if (Property
->Flags
!= KSPROPERTY_TYPE_GET
)
161 Irp
->IoStatus
.Status
= STATUS_NOT_IMPLEMENTED
;
162 Irp
->IoStatus
.Information
= 0;
163 return STATUS_NOT_IMPLEMENTED
;
168 case KSPROPERTY_TOPOLOGY_CATEGORIES
:
169 return KsHandleSizedListQuery(Irp
, Topology
->CategoriesCount
, sizeof(GUID
), Topology
->Categories
);
171 case KSPROPERTY_TOPOLOGY_NODES
:
172 return KsHandleSizedListQuery(Irp
, Topology
->TopologyNodesCount
, sizeof(GUID
), Topology
->TopologyNodes
);
174 case KSPROPERTY_TOPOLOGY_CONNECTIONS
:
175 return KsHandleSizedListQuery(Irp
, Topology
->TopologyConnectionsCount
, sizeof(KSTOPOLOGY_CONNECTION
), Topology
->TopologyConnections
);
177 case KSPROPERTY_TOPOLOGY_NAME
:
178 Node
= (KSP_NODE
*)Property
;
180 /* check for invalid node id */
181 if (Node
->NodeId
>= Topology
->TopologyNodesCount
)
183 /* invalid node id */
184 Irp
->IoStatus
.Information
= 0;
185 Status
= STATUS_INVALID_PARAMETER
;
189 /* check if there is a name supplied */
190 if (!IsEqualGUIDAligned(&Topology
->TopologyNodesNames
[Node
->NodeId
], &GUID_NULL
))
192 /* node name has been supplied */
193 Guid
= (LPGUID
)&Topology
->TopologyNodesNames
[Node
->NodeId
];
197 /* fallback to topology node type */
198 Guid
= (LPGUID
)&Topology
->TopologyNodes
[Node
->NodeId
];
201 /* read topology node name */
202 Status
= KspReadMediaCategory(Guid
, &KeyInfo
);
203 if (!NT_SUCCESS(Status
))
205 Irp
->IoStatus
.Information
= 0;
209 /* store result size */
210 Irp
->IoStatus
.Information
= KeyInfo
->DataLength
+ sizeof(WCHAR
);
212 /* check for buffer overflow */
213 if (KeyInfo
->DataLength
+ sizeof(WCHAR
) > IoStack
->Parameters
.DeviceIoControl
.OutputBufferLength
)
215 /* buffer too small */
216 Status
= STATUS_BUFFER_OVERFLOW
;
221 /* copy result buffer */
222 RtlMoveMemory(Irp
->UserBuffer
, &KeyInfo
->Data
, KeyInfo
->DataLength
);
224 /* zero terminate it */
225 ((LPWSTR
)Irp
->UserBuffer
)[KeyInfo
->DataLength
/ sizeof(WCHAR
)] = L
'\0';
232 Irp
->IoStatus
.Information
= 0;
233 Status
= STATUS_NOT_FOUND
;