io utilizzo queste funzioni
codice:
#Region " metodi di database "
    '----------------------------------------------------------------------------------
    'Restituisce Il prossimo Identificativo di una tabella oracle
    '----------------------------------------------------------------------------------
    Public Function ProssimoIDOracle%(ByVal StringaConnessione$, ByVal NomeTabella$, ByVal NomeCampoID$, Optional ByVal Where$ = "1=1")
        Dim sql$ = String.Format("SELECT DECODE(MAX({1}), NULL, 1, MAX({1}) + 1 ) AS PROSSIMO_ID FROM {0} WHERE {2}", NomeTabella, NomeCampoID, Where)

        Try
            Return CInt(RisultatoAggregazioneSQL(StringaConnessione, sql))
        Catch ex As Exception
            Throw
        End Try

    End Function

    '----------------------------------------------------------------------------------
    'Restituisce Il prossimo Identificativo di una tabella Access
    '----------------------------------------------------------------------------------
    Public Function ProssimoIDAccess%(ByVal StringaConnessione$, ByVal NomeTabella$, ByVal NomeCampoID$, Optional ByVal Where$ = "1=1")
        Dim sql$ = String.Format("SELECT IIF(ISNULL(MAX({1})),1, MAX({1}) + 1) AS PROSSIMO_ID FROM {0} WHERE {2}", NomeTabella, NomeCampoID, Where)

        Try
            Return CInt(RisultatoAggregazioneSQL(StringaConnessione, sql))
        Catch ex As Exception
            Throw
        End Try

    End Function
Aggiustale perchè queste danno il prossimo id utilizzabile, e non l'ultimo id inserito.

A proposito, le ho piazzate nelle famose librerie di uso generale e non hanno mai fallito (per adesso)