lib: add UnsupportedArchitectureException for triaged error message
This commit is contained in:
parent
173c4c61a4
commit
518d042e24
|
|
@ -80,7 +80,7 @@ class StubInferenceEngine : InferenceEngine {
|
||||||
// If coroutine is cancelled, propagate cancellation
|
// If coroutine is cancelled, propagate cancellation
|
||||||
throw e
|
throw e
|
||||||
} catch (e: Exception) {
|
} catch (e: Exception) {
|
||||||
_state.value = State.Error(e.message ?: "Unknown error during model loading")
|
_state.value = State.Error(e)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -107,7 +107,7 @@ class StubInferenceEngine : InferenceEngine {
|
||||||
// If coroutine is cancelled, propagate cancellation
|
// If coroutine is cancelled, propagate cancellation
|
||||||
throw e
|
throw e
|
||||||
} catch (e: Exception) {
|
} catch (e: Exception) {
|
||||||
_state.value = State.Error(e.message ?: "Unknown error during model loading")
|
_state.value = State.Error(e)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -142,13 +142,13 @@ class StubInferenceEngine : InferenceEngine {
|
||||||
_state.value = State.ModelReady
|
_state.value = State.ModelReady
|
||||||
throw e
|
throw e
|
||||||
} catch (e: Exception) {
|
} catch (e: Exception) {
|
||||||
_state.value = State.Error(e.message ?: "Unknown error during generation")
|
_state.value = State.Error(e)
|
||||||
throw e
|
throw e
|
||||||
}
|
}
|
||||||
}.catch { e ->
|
}.catch { e ->
|
||||||
// If it's not a cancellation, update state to error
|
// If it's not a cancellation, update state to error
|
||||||
if (e !is CancellationException) {
|
if (e !is CancellationException) {
|
||||||
_state.value = State.Error(e.message ?: "Unknown error during generation")
|
_state.value = State.Error(Exception(e))
|
||||||
}
|
}
|
||||||
throw e
|
throw e
|
||||||
}
|
}
|
||||||
|
|
@ -198,7 +198,7 @@ class StubInferenceEngine : InferenceEngine {
|
||||||
_state.value = State.ModelReady
|
_state.value = State.ModelReady
|
||||||
throw e
|
throw e
|
||||||
} catch (e: Exception) {
|
} catch (e: Exception) {
|
||||||
_state.value = State.Error(e.message ?: "Unknown error during benchmarking")
|
_state.value = State.Error(e)
|
||||||
"Error: ${e.message}"
|
"Error: ${e.message}"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,7 @@
|
||||||
package com.example.llama.ui.screens
|
package com.example.llama.ui.screens
|
||||||
|
|
||||||
import android.llama.cpp.InferenceEngine.State
|
import android.llama.cpp.InferenceEngine.State
|
||||||
|
import android.llama.cpp.UnsupportedArchitectureException
|
||||||
import androidx.activity.compose.BackHandler
|
import androidx.activity.compose.BackHandler
|
||||||
import androidx.compose.animation.AnimatedVisibility
|
import androidx.compose.animation.AnimatedVisibility
|
||||||
import androidx.compose.animation.expandVertically
|
import androidx.compose.animation.expandVertically
|
||||||
|
|
@ -112,7 +113,7 @@ fun ModelLoadingScreen(
|
||||||
|
|
||||||
// Check if we're in a loading state
|
// Check if we're in a loading state
|
||||||
val isLoading = engineState !is State.Initialized && engineState !is State.ModelReady
|
val isLoading = engineState !is State.Initialized && engineState !is State.ModelReady
|
||||||
val errorMessage = (engineState as? State.Error)?.errorMessage
|
val exception = (engineState as? State.Error)?.exception
|
||||||
|
|
||||||
// Handle back navigation requests
|
// Handle back navigation requests
|
||||||
BackHandler {
|
BackHandler {
|
||||||
|
|
@ -331,7 +332,7 @@ fun ModelLoadingScreen(
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
modifier = Modifier.fillMaxWidth().height(56.dp),
|
modifier = Modifier.fillMaxWidth().height(56.dp),
|
||||||
colors = if (errorMessage != null)
|
colors = if (exception != null)
|
||||||
ButtonDefaults.buttonColors(
|
ButtonDefaults.buttonColors(
|
||||||
disabledContainerColor = MaterialTheme.colorScheme.errorContainer.copy(alpha = 0.3f),
|
disabledContainerColor = MaterialTheme.colorScheme.errorContainer.copy(alpha = 0.3f),
|
||||||
disabledContentColor = MaterialTheme.colorScheme.onErrorContainer.copy(alpha = 0.7f)
|
disabledContentColor = MaterialTheme.colorScheme.onErrorContainer.copy(alpha = 0.7f)
|
||||||
|
|
@ -340,15 +341,21 @@ fun ModelLoadingScreen(
|
||||||
(!useSystemPrompt || hasActiveSystemPrompt)
|
(!useSystemPrompt || hasActiveSystemPrompt)
|
||||||
) {
|
) {
|
||||||
when {
|
when {
|
||||||
errorMessage != null -> {
|
exception != null -> {
|
||||||
|
val message = if (exception is UnsupportedArchitectureException) {
|
||||||
|
"Unsupported architecture: ${selectedModel?.metadata?.architecture?.architecture}"
|
||||||
|
} else {
|
||||||
|
exception.message ?: "Unknown error"
|
||||||
|
}
|
||||||
|
|
||||||
Icon(
|
Icon(
|
||||||
imageVector = Icons.Default.Error,
|
imageVector = Icons.Default.Error,
|
||||||
contentDescription = errorMessage,
|
contentDescription = message,
|
||||||
tint = MaterialTheme.colorScheme.error
|
tint = MaterialTheme.colorScheme.error
|
||||||
)
|
)
|
||||||
Spacer(modifier = Modifier.width(8.dp))
|
Spacer(modifier = Modifier.width(8.dp))
|
||||||
Text(
|
Text(
|
||||||
text = errorMessage,
|
text = message,
|
||||||
color = MaterialTheme.colorScheme.onErrorContainer
|
color = MaterialTheme.colorScheme.onErrorContainer
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -15,6 +15,8 @@ interface InferenceEngine {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Load a model from the given path.
|
* Load a model from the given path.
|
||||||
|
*
|
||||||
|
* @throws UnsupportedArchitectureException if model architecture not supported
|
||||||
*/
|
*/
|
||||||
suspend fun loadModel(pathToModel: String)
|
suspend fun loadModel(pathToModel: String)
|
||||||
|
|
||||||
|
|
@ -61,7 +63,7 @@ interface InferenceEngine {
|
||||||
|
|
||||||
object Generating : State()
|
object Generating : State()
|
||||||
|
|
||||||
data class Error(val errorMessage: String = "") : State()
|
data class Error(val exception: Exception) : State()
|
||||||
}
|
}
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
|
|
@ -81,3 +83,5 @@ val State.isModelLoaded: Boolean
|
||||||
this !is State.Initialized &&
|
this !is State.Initialized &&
|
||||||
this !is State.LoadingModel &&
|
this !is State.LoadingModel &&
|
||||||
this !is State.UnloadingModel
|
this !is State.UnloadingModel
|
||||||
|
|
||||||
|
class UnsupportedArchitectureException : Exception()
|
||||||
|
|
|
||||||
|
|
@ -2,6 +2,7 @@ package android.llama.cpp.internal
|
||||||
|
|
||||||
import android.llama.cpp.InferenceEngine
|
import android.llama.cpp.InferenceEngine
|
||||||
import android.llama.cpp.LLamaTier
|
import android.llama.cpp.LLamaTier
|
||||||
|
import android.llama.cpp.UnsupportedArchitectureException
|
||||||
import android.util.Log
|
import android.util.Log
|
||||||
import kotlinx.coroutines.CancellationException
|
import kotlinx.coroutines.CancellationException
|
||||||
import kotlinx.coroutines.CoroutineScope
|
import kotlinx.coroutines.CoroutineScope
|
||||||
|
|
@ -143,7 +144,7 @@ internal class InferenceEngineImpl private constructor(
|
||||||
_state.value = InferenceEngine.State.LoadingModel
|
_state.value = InferenceEngine.State.LoadingModel
|
||||||
load(pathToModel).let {
|
load(pathToModel).let {
|
||||||
// TODO-han.yin: find a better way to pass other error codes
|
// TODO-han.yin: find a better way to pass other error codes
|
||||||
if (it != 0) throw IOException("Unsupported architecture")
|
if (it != 0) throw UnsupportedArchitectureException()
|
||||||
}
|
}
|
||||||
prepare().let {
|
prepare().let {
|
||||||
if (it != 0) throw IOException("Failed to prepare resources")
|
if (it != 0) throw IOException("Failed to prepare resources")
|
||||||
|
|
@ -152,9 +153,8 @@ internal class InferenceEngineImpl private constructor(
|
||||||
_readyForSystemPrompt = true
|
_readyForSystemPrompt = true
|
||||||
_state.value = InferenceEngine.State.ModelReady
|
_state.value = InferenceEngine.State.ModelReady
|
||||||
} catch (e: Exception) {
|
} catch (e: Exception) {
|
||||||
val msg = e.message ?: "Unknown error"
|
Log.e(TAG, (e.message ?: "Error loading model") + "\n" + pathToModel, e)
|
||||||
Log.e(TAG, msg + "\n" + pathToModel, e)
|
_state.value = InferenceEngine.State.Error(e)
|
||||||
_state.value = InferenceEngine.State.Error(msg)
|
|
||||||
throw e
|
throw e
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -177,9 +177,10 @@ internal class InferenceEngineImpl private constructor(
|
||||||
_state.value = InferenceEngine.State.ProcessingSystemPrompt
|
_state.value = InferenceEngine.State.ProcessingSystemPrompt
|
||||||
processSystemPrompt(prompt).let { result ->
|
processSystemPrompt(prompt).let { result ->
|
||||||
if (result != 0) {
|
if (result != 0) {
|
||||||
val errorMessage = "Failed to process system prompt: $result"
|
RuntimeException("Failed to process system prompt: $result").also {
|
||||||
_state.value = InferenceEngine.State.Error(errorMessage)
|
_state.value = InferenceEngine.State.Error(it)
|
||||||
throw IllegalStateException(errorMessage)
|
throw it
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Log.i(TAG, "System prompt processed! Awaiting user prompt...")
|
Log.i(TAG, "System prompt processed! Awaiting user prompt...")
|
||||||
|
|
@ -225,7 +226,7 @@ internal class InferenceEngineImpl private constructor(
|
||||||
throw e
|
throw e
|
||||||
} catch (e: Exception) {
|
} catch (e: Exception) {
|
||||||
Log.e(TAG, "Error during generation!", e)
|
Log.e(TAG, "Error during generation!", e)
|
||||||
_state.value = InferenceEngine.State.Error(e.message ?: "Unknown error")
|
_state.value = InferenceEngine.State.Error(e)
|
||||||
throw e
|
throw e
|
||||||
}
|
}
|
||||||
}.flowOn(llamaDispatcher)
|
}.flowOn(llamaDispatcher)
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue