Beispiel #1
0
NTSTATUS
GnttabInitialize(
    IN  PXENBUS_FDO             Fdo,
    OUT PXENBUS_GNTTAB_CONTEXT  *Context
    )
{
    NTSTATUS                    status;

    Trace("====>\n");

    *Context = __GnttabAllocate(sizeof (XENBUS_GNTTAB_CONTEXT));

    status = STATUS_NO_MEMORY;
    if (*Context == NULL)
        goto fail1;

    status = RangeSetGetInterface(FdoGetRangeSetContext(Fdo),
                                  XENBUS_RANGE_SET_INTERFACE_VERSION_MAX,
                                  (PINTERFACE)&(*Context)->RangeSetInterface,
                                  sizeof ((*Context)->RangeSetInterface));
    ASSERT(NT_SUCCESS(status));
    ASSERT((*Context)->RangeSetInterface.Interface.Context != NULL);

    status = CacheGetInterface(FdoGetCacheContext(Fdo),
                               XENBUS_CACHE_INTERFACE_VERSION_MAX,
                               (PINTERFACE)&(*Context)->CacheInterface,
                               sizeof ((*Context)->CacheInterface));
    ASSERT(NT_SUCCESS(status));
    ASSERT((*Context)->CacheInterface.Interface.Context != NULL);

    status = SuspendGetInterface(FdoGetSuspendContext(Fdo),
                                 XENBUS_SUSPEND_INTERFACE_VERSION_MAX,
                                 (PINTERFACE)&(*Context)->SuspendInterface,
                                 sizeof ((*Context)->SuspendInterface));
    ASSERT(NT_SUCCESS(status));
    ASSERT((*Context)->SuspendInterface.Interface.Context != NULL);

    status = DebugGetInterface(FdoGetDebugContext(Fdo),
                               XENBUS_DEBUG_INTERFACE_VERSION_MAX,
                               (PINTERFACE)&(*Context)->DebugInterface,
                               sizeof ((*Context)->DebugInterface));
    ASSERT(NT_SUCCESS(status));
    ASSERT((*Context)->DebugInterface.Interface.Context != NULL);

    InitializeListHead(&(*Context)->List);
    KeInitializeSpinLock(&(*Context)->Lock);

    status = HashTableCreate(&(*Context)->MapTable);
    if (!NT_SUCCESS(status))
        goto fail2;

    (*Context)->Fdo = Fdo;

    Trace("<====\n");

    return STATUS_SUCCESS;

fail2:
    Error("fail2\n");

fail1:
    Error("fail1 (%08x)\n", status);

    return status;
}
Beispiel #2
0
static NTSTATUS
GnttabCreateCache(
    IN  PINTERFACE              Interface,
    IN  const CHAR              *Name,
    IN  ULONG                   Reservation,
    IN  VOID                    (*AcquireLock)(PVOID),
    IN  VOID                    (*ReleaseLock)(PVOID),
    IN  PVOID                   Argument,
    OUT PXENBUS_GNTTAB_CACHE    *Cache
    )
{
    PXENBUS_GNTTAB_CONTEXT      Context = Interface->Context;
    KIRQL                       Irql;
    NTSTATUS                    status;

    *Cache = __GnttabAllocate(sizeof (XENBUS_GNTTAB_CACHE));

    status = STATUS_NO_MEMORY;
    if (*Cache == NULL)
        goto fail1;

    (*Cache)->Context = Context;

    status = RtlStringCbPrintfA((*Cache)->Name,
                                sizeof ((*Cache)->Name),
                                "%s_gnttab",
                                Name);
    if (!NT_SUCCESS(status))
        goto fail2;

    (*Cache)->AcquireLock = AcquireLock;
    (*Cache)->ReleaseLock = ReleaseLock;
    (*Cache)->Argument = Argument;

    status = XENBUS_CACHE(Create,
                          &Context->CacheInterface,
                          (*Cache)->Name,
                          sizeof (XENBUS_GNTTAB_ENTRY),
                          Reservation,
                          GnttabEntryCtor,
                          GnttabEntryDtor,
                          GnttabAcquireLock,
                          GnttabReleaseLock,
                          *Cache,
                          &(*Cache)->Cache);
    if (!NT_SUCCESS(status))
        goto fail3;

    KeAcquireSpinLock(&Context->Lock, &Irql);
    InsertTailList(&Context->List, &(*Cache)->ListEntry);
    KeReleaseSpinLock(&Context->Lock, Irql);

    return STATUS_SUCCESS;

fail3:
    Error("fail3\n");

    (*Cache)->Argument = NULL;
    (*Cache)->ReleaseLock = NULL;
    (*Cache)->AcquireLock = NULL;

    RtlZeroMemory((*Cache)->Name, sizeof ((*Cache)->Name));
    
fail2:
    Error("fail2\n");

    (*Cache)->Context = NULL;

    ASSERT(IsZeroMemory(*Cache, sizeof (XENBUS_GNTTAB_CACHE)));
    __GnttabFree(*Cache);

fail1:
    Error("fail1 (%08x)\n", status);

    return status;
}
Beispiel #3
0
static NTSTATUS
GnttabMapForeignPages(
    IN  PINTERFACE              Interface,
    IN  USHORT                  Domain,
    IN  ULONG                   NumberPages,
    IN  PULONG                  References,
    IN  BOOLEAN                 ReadOnly,
    OUT PHYSICAL_ADDRESS        *Address
    )
{
    PXENBUS_GNTTAB_CONTEXT      Context = Interface->Context;
    LONG                        PageIndex;
    PHYSICAL_ADDRESS            PageAddress;
    PXENBUS_GNTTAB_MAP_ENTRY    MapEntry;
    NTSTATUS                    status;

    status = FdoAllocateIoSpace(Context->Fdo,
                                NumberPages * PAGE_SIZE,
                                Address);
    if (!NT_SUCCESS(status))
        goto fail1;

    MapEntry = __GnttabAllocate(FIELD_OFFSET(XENBUS_GNTTAB_MAP_ENTRY,
                                             MapHandles) +
                                (NumberPages * sizeof (ULONG)));

    status = STATUS_NO_MEMORY;
    if (MapEntry == NULL)
        goto fail2;

    PageAddress.QuadPart = Address->QuadPart;
    MapEntry->NumberPages = NumberPages;

    for (PageIndex = 0; PageIndex < (LONG)NumberPages; PageIndex++) {
        status = GrantTableMapForeignPage(Domain,
                                          References[PageIndex],
                                          PageAddress,
                                          ReadOnly,
                                          &MapEntry->MapHandles[PageIndex]);
        if (!NT_SUCCESS(status))
            goto fail3;

        PageAddress.QuadPart += PAGE_SIZE;
    }

    status = HashTableAdd(Context->MapTable,
                          (ULONG_PTR)Address->QuadPart,
                          (ULONG_PTR)MapEntry);
    if (!NT_SUCCESS(status))
        goto fail4;

    return STATUS_SUCCESS;

fail4:
    Error("fail4\n");

fail3:
    Error("fail3\n");

    while (--PageIndex >= 0) {
        PageAddress.QuadPart -= PAGE_SIZE;
        (VOID) GrantTableUnmapForeignPage(MapEntry->MapHandles[PageIndex],
                                          PageAddress);
    }

    __GnttabFree(MapEntry);

fail2:
    Error("fail2\n");

    FdoFreeIoSpace(Context->Fdo, *Address, NumberPages * PAGE_SIZE);

fail1:
    Error("fail1: (%08x)\n", status);

    return status;
}
Beispiel #4
0
static NTSTATUS
GnttabCreateCache(
    IN  PXENBUS_GNTTAB_CONTEXT  Context,
    IN  const CHAR              *Name,
    IN  ULONG                   Reservation,
    IN  VOID                    (*AcquireLock)(PVOID),
    IN  VOID                    (*ReleaseLock)(PVOID),
    IN  PVOID                   Argument,
    OUT PXENBUS_GNTTAB_CACHE    *Cache
)
{
    NTSTATUS                    status;

    *Cache = __GnttabAllocate(sizeof (XENBUS_GNTTAB_CACHE));

    status = STATUS_NO_MEMORY;
    if (*Cache == NULL)
        goto fail1;

    (*Cache)->Context = Context;

    status = RtlStringCbPrintfA((*Cache)->Name,
                                sizeof ((*Cache)->Name),
                                "%s_gnttab",
                                Name);
    if (!NT_SUCCESS(status))
        goto fail2;

    (*Cache)->AcquireLock = AcquireLock;
    (*Cache)->ReleaseLock = ReleaseLock;
    (*Cache)->Argument = Argument;

    status = CACHE(Create,
                   Context->CacheInterface,
                   (*Cache)->Name,
                   sizeof (XENBUS_GNTTAB_DESCRIPTOR),
                   Reservation,
                   GnttabDescriptorCtor,
                   GnttabDescriptorDtor,
                   GnttabAcquireLock,
                   GnttabReleaseLock,
                   *Cache,
                   &(*Cache)->Cache);
    if (!NT_SUCCESS(status))
        goto fail3;

    return STATUS_SUCCESS;

fail3:
    Error("fail3\n");

    (*Cache)->Argument = NULL;
    (*Cache)->ReleaseLock = NULL;
    (*Cache)->AcquireLock = NULL;

    RtlZeroMemory((*Cache)->Name, sizeof ((*Cache)->Name));

fail2:
    Error("fail2\n");

    (*Cache)->Context = NULL;

    ASSERT(IsZeroMemory(*Cache, sizeof (XENBUS_GNTTAB_CACHE)));
    __GnttabFree(*Cache);

fail1:
    Error("fail1 (%08x)\n", status);

    return status;
}