MCPcopy Create free account
hub / github.com/ashvardanian/StringZilla / NeedlemanWunsch_call

Function NeedlemanWunsch_call

python/stringzillas.c:1010–1150  ·  view source on GitHub ↗

Source from the content-addressed store, hash-verified

1008}
1009
1010static PyObject *NeedlemanWunsch_call(NeedlemanWunsch *self, PyObject *args, PyObject *kwargs) {
1011 PyObject *a_obj = NULL, *b_obj = NULL, *device_obj = NULL, *out_obj = NULL;
1012
1013 static char *kwlist[] = {"a", "b", "device", "out", NULL};
1014 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "OO|OO", kwlist, &a_obj, &b_obj, &device_obj, &out_obj)) return NULL;
1015
1016 // Get device handle
1017 szs_device_scope_t device_handle = default_device_scope;
1018 if (device_obj && device_obj != Py_None) {
1019 if (!PyObject_IsInstance(device_obj, (PyObject *)&DeviceScopeType)) {
1020 PyErr_SetString(PyExc_TypeError, "device must be a DeviceScope instance");
1021 return NULL;
1022 }
1023 device_handle = ((DeviceScope *)device_obj)->handle;
1024 }
1025
1026 sz_size_t kernel_input_size = 0;
1027 void const *kernel_a_texts_punned = NULL;
1028 void const *kernel_b_texts_punned = NULL;
1029 sz_status_t (*kernel_punned)(szs_needleman_wunsch_scores_t, szs_device_scope_t, void const *, void const *,
1030 sz_ssize_t *, sz_size_t, char const **) = NULL;
1031
1032 // Swap allocators only when using CUDA with a GPU device (inputs must be unified)
1033 if (requires_unified_memory(self->capabilities))
1034 if (!try_swap_to_unified_allocator(a_obj) || !try_swap_to_unified_allocator(b_obj)) return NULL;
1035
1036 // Handle 32-bit tape inputs
1037 sz_sequence_u32tape_t a_u32tape, b_u32tape;
1038 sz_bool_t a_is_u32tape = sz_py_export_strings_as_u32tape( //
1039 a_obj, &a_u32tape.data, &a_u32tape.offsets, &a_u32tape.count);
1040 sz_bool_t b_is_u32tape = sz_py_export_strings_as_u32tape( //
1041 b_obj, &b_u32tape.data, &b_u32tape.offsets, &b_u32tape.count);
1042 if (a_is_u32tape && b_is_u32tape) {
1043 if (a_u32tape.count != b_u32tape.count) {
1044 PyErr_SetString(PyExc_ValueError, "Input sequences must have the same length");
1045 return NULL;
1046 }
1047 kernel_input_size = a_u32tape.count;
1048 kernel_punned = szs_needleman_wunsch_scores_u32tape;
1049 kernel_a_texts_punned = &a_u32tape;
1050 kernel_b_texts_punned = &b_u32tape;
1051 }
1052
1053 // Handle 64-bit tape inputs
1054 sz_sequence_u64tape_t a_u64tape, b_u64tape;
1055 sz_bool_t a_is_u64tape = !a_is_u32tape && sz_py_export_strings_as_u64tape( //
1056 a_obj, &a_u64tape.data, &a_u64tape.offsets, &a_u64tape.count);
1057 sz_bool_t b_is_u64tape = !b_is_u32tape && sz_py_export_strings_as_u64tape( //
1058 b_obj, &b_u64tape.data, &b_u64tape.offsets, &b_u64tape.count);
1059 if (a_is_u64tape && b_is_u64tape) {
1060 if (a_u64tape.count != b_u64tape.count) {
1061 PyErr_SetString(PyExc_ValueError, "Input sequences must have the same length");
1062 return NULL;
1063 }
1064 kernel_input_size = a_u64tape.count;
1065 kernel_punned = szs_needleman_wunsch_scores_u64tape;
1066 kernel_a_texts_punned = &a_u64tape;
1067 kernel_b_texts_punned = &b_u64tape;

Callers

nothing calls this directly

Tested by

no test coverage detected

Used in the wild real call sites across dependent graphs

searching dependent graphs…