char-fork/llama.cpp

git clone https://git.t4t.associates/char-fork/llama.cpp

Georgi Gerganovggml : update ggml_prec specification (#26675)5a6caa05f

char/aliceai-t5-moe
253.7 KiB8139 linesraw
1#define _CRT_SECURE_NO_DEPRECATE // Disables "unsafe" warnings on Windows
2#define _USE_MATH_DEFINES // For M_PI on MSVC
3
4#include "ggml-version.h"
5#include "ggml-backend.h"
6#include "ggml-impl.h"
7#include "ggml-threading.h"
8#include "ggml-cpu.h"
9#include "ggml.h"
10
11// FIXME: required here for quantization functions
12#include "ggml-quants.h"
13
14#ifdef GGML_USE_CPU_HBM
15#include <hbwmalloc.h>
16#endif
17
18#if defined(_MSC_VER) || defined(__MINGW32__)
19#include <malloc.h> // using malloc.h with MSC/MINGW
20#elif !defined(__FreeBSD__) && !defined(__NetBSD__) && !defined(__OpenBSD__)
21#include <alloca.h>
22#endif
23
24#include <assert.h>
25#include <errno.h>
26#include <time.h>
27#include <math.h>
28#include <stdlib.h>
29#include <string.h>
30#include <stdint.h>
31#include <inttypes.h>
32#include <stdio.h>
33#include <float.h>
34#include <limits.h>
35#include <stdarg.h>
36#include <signal.h>
37#if defined(__gnu_linux__)
38#include <syscall.h>
39#endif
40
41#if defined(__APPLE__)
42#include <unistd.h>
43#include <mach/mach.h>
44#include <TargetConditionals.h>
45#endif
46
47#if defined(_WIN32)
48#define WIN32_LEAN_AND_MEAN
49#ifndef NOMINMAX
50    #define NOMINMAX
51#endif
52#include <windows.h>
53#endif
54
55#define UNUSED GGML_UNUSED
56
57uint64_t ggml_graph_next_uid(void) {
58#ifdef _MSC_VER
59#if defined(_WIN32)
60    static volatile LONG counter = 1;
61    return (uint64_t) InterlockedIncrement(&counter) - 1;
62#else
63    static volatile long long counter = 1;
64    return (uint64_t) _InterlockedIncrement64(&counter) - 1;
65#endif
66#else
67    static uint64_t counter = 1;
68    return __atomic_fetch_add(&counter, 1, __ATOMIC_RELAXED);
69#endif
70}
71
72// Needed for ggml_fp32_to_bf16_row()
73#if defined(__AVX512BF16__)
74#if defined(_MSC_VER)
75#define m512i(p) p
76#else
77#include <immintrin.h>
78#define m512i(p) (__m512i)(p)
79#endif // defined(_MSC_VER)
80#endif // defined(__AVX512BF16__)
81
82#if defined(__linux__) || \
83    defined(__FreeBSD__) || defined(__NetBSD__) || defined(__OpenBSD__) || \
84    (defined(__APPLE__) && !TARGET_OS_TV && !TARGET_OS_WATCH)
85
86#include <unistd.h>
87#include <sys/types.h>
88#include <sys/stat.h>
89#include <sys/wait.h>
90#if defined(__linux__)
91#include <sys/prctl.h>
92#endif
93
94#if defined(__ANDROID__)
95#include <unwind.h>
96#include <dlfcn.h>
97#include <stdio.h>
98
99struct backtrace_state {
100    void ** current;
101    void ** end;
102};
103
104static _Unwind_Reason_Code unwind_callback(struct _Unwind_Context* context, void* arg) {
105    struct backtrace_state * state = (struct backtrace_state *)arg;
106    uintptr_t pc = _Unwind_GetIP(context);
107    if (pc) {
108        if (state->current == state->end) {
109            return _URC_END_OF_STACK;
110        } else {
111            *state->current++ = (void*)pc;
112        }
113    }
114    return _URC_NO_REASON;
115}
116
117static void ggml_print_backtrace_symbols(void) {
118    const int max = 100;
119    void* buffer[max];
120
121    struct backtrace_state state = {buffer, buffer + max};
122    _Unwind_Backtrace(unwind_callback, &state);
123
124    int count = state.current - buffer;
125
126    for (int idx = 0; idx < count; ++idx) {
127        const void * addr = buffer[idx];
128        const char * symbol = "";
129
130        Dl_info info;
131        if (dladdr(addr, &info) && info.dli_sname) {
132            symbol = info.dli_sname;
133        }
134
135        fprintf(stderr, "%d: %p %s\n", idx, addr, symbol);
136    }
137}
138#elif defined(__linux__) && defined(__GLIBC__)
139#include <execinfo.h>
140static void ggml_print_backtrace_symbols(void) {
141    void * trace[100];
142    int nptrs = backtrace(trace, sizeof(trace)/sizeof(trace[0]));
143    backtrace_symbols_fd(trace, nptrs, STDERR_FILENO);
144}
145#elif defined(__APPLE__)
146#include <execinfo.h>
147static void ggml_print_backtrace_symbols(void) {
148    void * trace[100];
149    int nptrs = backtrace(trace, sizeof(trace)/sizeof(trace[0]));
150    backtrace_symbols_fd(trace, nptrs, STDERR_FILENO);
151}
152#else
153static void ggml_print_backtrace_symbols(void) {
154    // platform not supported
155}
156#endif
157
158void ggml_print_backtrace(void) {
159    const char * GGML_NO_BACKTRACE = getenv("GGML_NO_BACKTRACE");
160    if (GGML_NO_BACKTRACE) {
161        return;
162    }
163#if defined(__APPLE__)
164    // On macOS, fork+debugger attachment is problematic due to:
165    // 1. libdispatch "poisons" forked child processes
166    // 2. lldb has issues attaching to parent from forked child
167    // Use simple backtrace() instead to avoid Terminal.app crashes
168    const char * GGML_BACKTRACE_LLDB = getenv("GGML_BACKTRACE_LLDB");
169    if (!GGML_BACKTRACE_LLDB) {
170        fprintf(stderr, "WARNING: Using native backtrace. Set GGML_BACKTRACE_LLDB for more info.\n");
171        fprintf(stderr, "WARNING: GGML_BACKTRACE_LLDB may cause native MacOS Terminal.app to crash.\n");
172        fprintf(stderr, "See: https://github.com/ggml-org/llama.cpp/pull/17869\n");
173        ggml_print_backtrace_symbols();
174        return;
175    }
176#endif
177#if defined(__linux__)
178    FILE * f = fopen("/proc/self/status", "r");
179    size_t size = 0;
180    char * line = NULL;
181    ssize_t length = 0;
182    while ((length = getline(&line, &size, f)) > 0) {
183        if (!strncmp(line, "TracerPid:", sizeof("TracerPid:") - 1) &&
184            (length != sizeof("TracerPid:\t0\n") - 1 || line[length - 2] != '0')) {
185            // Already being debugged, and the breakpoint is the later abort()
186            free(line);
187            fclose(f);
188            return;
189        }
190    }
191    free(line);
192    fclose(f);
193    int lock[2] = { -1, -1 };
194    (void) !pipe(lock); // Don't start gdb until after PR_SET_PTRACER
195#endif
196    const int parent_pid = getpid();
197    const int child_pid = fork();
198    if (child_pid < 0) { // error
199#if defined(__linux__)
200        close(lock[1]);
201        close(lock[0]);
202#endif
203        return;
204    } else if (child_pid == 0) { // child
205        char attach[32];
206        snprintf(attach, sizeof(attach), "attach %d", parent_pid);
207#if defined(__linux__)
208        close(lock[1]);
209        (void) !read(lock[0], lock, 1);
210        close(lock[0]);
211#endif
212        // try gdb
213        execlp("gdb", "gdb", "--batch",
214            "-ex", "set style enabled on",
215            "-ex", attach,
216            "-ex", "bt -frame-info source-and-location",
217            "-ex", "detach",
218            "-ex", "quit",
219            (char *) NULL);
220        // try lldb
221        execlp("lldb", "lldb", "--batch",
222            "-o", "bt",
223            "-o", "quit",
224            "-p", &attach[sizeof("attach ") - 1],
225            (char *) NULL);
226        // gdb failed, fallback to backtrace_symbols
227        ggml_print_backtrace_symbols();
228        _Exit(0);
229    } else { // parent
230#if defined(__linux__)
231        prctl(PR_SET_PTRACER, child_pid);
232        close(lock[1]);
233        close(lock[0]);
234#endif
235        waitpid(child_pid, NULL, 0);
236    }
237}
238#else
239void ggml_print_backtrace(void) {
240    // platform not supported
241}
242#endif
243
244static ggml_abort_callback_t g_abort_callback = NULL;
245
246// Set the abort callback (passing null will restore original abort functionality: printing a message to stdout)
247GGML_API ggml_abort_callback_t ggml_set_abort_callback(ggml_abort_callback_t callback) {
248    ggml_abort_callback_t ret_val = g_abort_callback;
249    g_abort_callback = callback;
250    return ret_val;
251}
252
253void ggml_abort(const char * file, int line, const char * fmt, ...) {
254    fflush(stdout);
255
256    char message[2048];
257    int offset = snprintf(message, sizeof(message), "%s:%d: ", file, line);
258
259    va_list args;
260    va_start(args, fmt);
261    vsnprintf(message + offset, sizeof(message) - offset, fmt, args);
262    va_end(args);
263
264    if (g_abort_callback) {
265        g_abort_callback(message);
266    } else {
267        // default: print error and backtrace to stderr
268        fprintf(stderr, "%s\n", message);
269        ggml_print_backtrace();
270    }
271
272    abort();
273}
274
275// ggml_print_backtrace is registered with std::set_terminate by ggml.cpp
276
277//
278// logging
279//
280
281struct ggml_logger_state {
282    ggml_log_callback log_callback;
283    void * log_callback_user_data;
284};
285static struct ggml_logger_state g_logger_state = {ggml_log_callback_default, NULL};
286
287static void ggml_log_internal_v(enum ggml_log_level level, const char * format, va_list args) {
288    if (format == NULL) {
289        return;
290    }
291    va_list args_copy;
292    va_copy(args_copy, args);
293    char buffer[128];
294    int len = vsnprintf(buffer, 128, format, args);
295    if (len < 128) {
296        g_logger_state.log_callback(level, buffer, g_logger_state.log_callback_user_data);
297    } else {
298        char * buffer2 = (char *) calloc(len + 1, sizeof(char));
299        vsnprintf(buffer2, len + 1, format, args_copy);
300        buffer2[len] = 0;
301        g_logger_state.log_callback(level, buffer2, g_logger_state.log_callback_user_data);
302        free(buffer2);
303    }
304    va_end(args_copy);
305}
306
307void ggml_log_internal(enum ggml_log_level level, const char * format, ...) {
308    va_list args;
309    va_start(args, format);
310    ggml_log_internal_v(level, format, args);
311    va_end(args);
312}
313
314void ggml_log_callback_default(enum ggml_log_level level, const char * text, void * user_data) {
315    (void) level;
316    (void) user_data;
317    fputs(text, stderr);
318    fflush(stderr);
319}
320
321//
322// end of logging block
323//
324
325#ifdef GGML_USE_ACCELERATE
326// uncomment to use vDSP for soft max computation
327// note: not sure if it is actually faster
328//#define GGML_SOFT_MAX_ACCELERATE
329#endif
330
331
332void * ggml_aligned_malloc(size_t size) {
333#if defined(__s390x__)
334    const int alignment = 256;
335#else
336    const int alignment = 64;
337#endif
338
339#if defined(_MSC_VER) || defined(__MINGW32__)
340    return _aligned_malloc(size, alignment);
341#else
342    if (size == 0) {
343        GGML_LOG_WARN("Behavior may be unexpected when allocating 0 bytes for ggml_aligned_malloc!\n");
344        return NULL;
345    }
346    void * aligned_memory = NULL;
347  #ifdef GGML_USE_CPU_HBM
348    int result = hbw_posix_memalign(&aligned_memory, alignment, size);
349  #elif TARGET_OS_OSX
350    GGML_UNUSED(alignment);
351    kern_return_t alloc_status = vm_allocate((vm_map_t) mach_task_self(), (vm_address_t *) &aligned_memory, size, VM_FLAGS_ANYWHERE);
352    int result = EFAULT;
353    switch (alloc_status) {
354        case KERN_SUCCESS:
355            result = 0;
356            break;
357        case KERN_INVALID_ADDRESS:
358            result = EINVAL;
359            break;
360        case KERN_NO_SPACE:
361            result = ENOMEM;
362            break;
363        default:
364            result = EFAULT;
365            break;
366    }
367  #else
368    int result = posix_memalign(&aligned_memory, alignment, size);
369  #endif
370    if (result != 0) {
371        // Handle allocation failure
372        const char *error_desc = "unknown allocation error";
373        switch (result) {
374            case EINVAL:
375                error_desc = "invalid alignment value";
376                break;
377            case ENOMEM:
378                error_desc = "insufficient memory";
379                break;
380        }
381        GGML_LOG_ERROR("%s: %s (attempted to allocate %6.2f MB)\n", __func__, error_desc, size/(1024.0*1024.0));
382        return NULL;
383    }
384    return aligned_memory;
385#endif
386}
387
388void ggml_aligned_free(void * ptr, size_t size) {
389    GGML_UNUSED(size);
390#if defined(_MSC_VER) || defined(__MINGW32__)
391    _aligned_free(ptr);
392#elif GGML_USE_CPU_HBM
393    if (ptr != NULL) {
394        hbw_free(ptr);
395    }
396#elif TARGET_OS_OSX
397    if (ptr != NULL) {
398        vm_deallocate((vm_map_t)mach_task_self(), (vm_address_t)ptr, size);
399    }
400#else
401    free(ptr);
402#endif
403}
404
405
406inline static void * ggml_malloc(size_t size) {
407    if (size == 0) {
408        GGML_LOG_WARN("Behavior may be unexpected when allocating 0 bytes for ggml_malloc!\n");
409        return NULL;
410    }
411    void * result = malloc(size);
412    if (result == NULL) {
413        GGML_LOG_ERROR("%s: failed to allocate %6.2f MB\n", __func__, size/(1024.0*1024.0));
414        GGML_ABORT("fatal error");
415    }
416    return result;
417}
418
419// calloc
420inline static void * ggml_calloc(size_t num, size_t size) {
421    if (num == 0 || size == 0) {
422        GGML_LOG_WARN("Behavior may be unexpected when allocating 0 bytes for ggml_calloc!\n");
423        return NULL;
424    }
425    void * result = calloc(num, size);
426    if (result == NULL) {
427        GGML_LOG_ERROR("%s: failed to allocate %6.2f MB\n", __func__, size/(1024.0*1024.0));
428        GGML_ABORT("fatal error");
429    }
430    return result;
431}
432
433#define GGML_MALLOC(size)      ggml_malloc(size)
434#define GGML_CALLOC(num, size) ggml_calloc(num, size)
435
436#define GGML_FREE(ptr) free(ptr)
437
438const char * ggml_status_to_string(enum ggml_status status) {
439    switch (status) {
440        case GGML_STATUS_ALLOC_FAILED: return "GGML status: error (failed to allocate memory)";
441        case GGML_STATUS_FAILED:       return "GGML status: error (operation failed)";
442        case GGML_STATUS_SUCCESS:      return "GGML status: success";
443        case GGML_STATUS_ABORTED:      return "GGML status: warning (operation aborted)";
444    }
445
446    return "GGML status: unknown";
447}
448
449float ggml_fp16_to_fp32(ggml_fp16_t x) {
450#define ggml_fp16_to_fp32 do_not_use__ggml_fp16_to_fp32__in_ggml
451    return GGML_FP16_TO_FP32(x);
452}
453
454ggml_fp16_t ggml_fp32_to_fp16(float x) {
455#define ggml_fp32_to_fp16 do_not_use__ggml_fp32_to_fp16__in_ggml
456    return GGML_FP32_TO_FP16(x);
457}
458
459float ggml_bf16_to_fp32(ggml_bf16_t x) {
460#define ggml_bf16_to_fp32 do_not_use__ggml_bf16_to_fp32__in_ggml
461    return GGML_BF16_TO_FP32(x);  // it just left shifts
462}
463
464ggml_bf16_t ggml_fp32_to_bf16(float x) {
465#define ggml_fp32_to_bf16 do_not_use__ggml_fp32_to_bf16__in_ggml
466    return GGML_FP32_TO_BF16(x);
467}
468
469void ggml_fp16_to_fp32_row(const ggml_fp16_t * x, float * y, int64_t n) {
470    for (int64_t i = 0; i < n; i++) {
471        y[i] = GGML_FP16_TO_FP32(x[i]);
472    }
473}
474
475void ggml_fp32_to_fp16_row(const float * x, ggml_fp16_t * y, int64_t n) {
476    int i = 0;
477    for (; i < n; ++i) {
478        y[i] = GGML_FP32_TO_FP16(x[i]);
479    }
480}
481
482void ggml_bf16_to_fp32_row(const ggml_bf16_t * x, float * y, int64_t n) {
483    int i = 0;
484    for (; i < n; ++i) {
485        y[i] = GGML_BF16_TO_FP32(x[i]);
486    }
487}
488
489void ggml_fp32_to_bf16_row_ref(const float * x, ggml_bf16_t * y, int64_t n) {
490    for (int i = 0; i < n; i++) {
491        y[i] = ggml_compute_fp32_to_bf16(x[i]);
492    }
493}
494
495void ggml_fp32_to_bf16_row(const float * x, ggml_bf16_t * y, int64_t n) {
496  int i = 0;
497#if defined(__AVX512BF16__)
498  // subnormals are flushed to zero on this platform
499  for (; i + 32 <= n; i += 32) {
500        _mm512_storeu_si512(
501            (__m512i *)(y + i),
502            m512i(_mm512_cvtne2ps_pbh(_mm512_loadu_ps(x + i + 16),
503                                _mm512_loadu_ps(x + i))));
504  }
505#endif
506    for (; i < n; i++) {
507        y[i] = GGML_FP32_TO_BF16(x[i]);
508    }
509}
510
511bool ggml_guid_matches(ggml_guid_t guid_a, ggml_guid_t guid_b) {
512    return memcmp(guid_a, guid_b, sizeof(ggml_guid)) == 0;
513}
514
515const char * ggml_version(void) {
516    return GGML_VERSION;
517}
518
519const char * ggml_commit(void) {
520    return GGML_COMMIT;
521}
522
523//
524// timing
525//
526
527#if defined(_MSC_VER) || defined(__MINGW32__)
528static int64_t timer_freq, timer_start;
529static BOOL CALLBACK ggml_time_init_once(PINIT_ONCE once, PVOID param, PVOID *ctx) {
530    UNUSED(once);
531    UNUSED(param);
532    UNUSED(ctx);
533
534    LARGE_INTEGER t;
535    QueryPerformanceFrequency(&t);
536    timer_freq = t.QuadPart;
537
538    // The multiplication by 1000 or 1000000 below can cause an overflow if timer_freq
539    // and the uptime is high enough.
540    // We subtract the program start time to reduce the likelihood of that happening.
541    QueryPerformanceCounter(&t);
542    timer_start = t.QuadPart;
543
544    return TRUE;
545}
546void ggml_time_init(void) {
547    static INIT_ONCE once = INIT_ONCE_STATIC_INIT;
548    InitOnceExecuteOnce(&once, ggml_time_init_once, NULL, NULL);
549}
550int64_t ggml_time_ms(void) {
551    LARGE_INTEGER t;
552    QueryPerformanceCounter(&t);
553    return ((t.QuadPart-timer_start) * 1000) / timer_freq;
554}
555int64_t ggml_time_us(void) {
556    LARGE_INTEGER t;
557    QueryPerformanceCounter(&t);
558    return ((t.QuadPart-timer_start) * 1000000) / timer_freq;
559}
560#else
561void ggml_time_init(void) {}
562int64_t ggml_time_ms(void) {
563    struct timespec ts;
564    clock_gettime(CLOCK_MONOTONIC, &ts);
565    return (int64_t)ts.tv_sec*1000 + (int64_t)ts.tv_nsec/1000000;
566}
567
568int64_t ggml_time_us(void) {
569    struct timespec ts;
570    clock_gettime(CLOCK_MONOTONIC, &ts);
571    return (int64_t)ts.tv_sec*1000000 + (int64_t)ts.tv_nsec/1000;
572}
573#endif
574
575int64_t ggml_cycles(void) {
576    return clock();
577}
578
579int64_t ggml_cycles_per_ms(void) {
580    return CLOCKS_PER_SEC/1000;
581}
582
583//
584// cross-platform UTF-8 file paths
585//
586
587#ifdef _WIN32
588static wchar_t * ggml_mbstowcs(const char * mbs) {
589    int wlen = MultiByteToWideChar(CP_UTF8, 0, mbs, -1, NULL, 0);
590    if (!wlen) {
591        errno = EINVAL;
592        return NULL;
593    }
594
595    wchar_t * wbuf = GGML_MALLOC(wlen * sizeof(wchar_t));
596    wlen = MultiByteToWideChar(CP_UTF8, 0, mbs, -1, wbuf, wlen);
597    if (!wlen) {
598        GGML_FREE(wbuf);
599        errno = EINVAL;
600        return NULL;
601    }
602
603    return wbuf;
604}
605#endif
606
607FILE * ggml_fopen(const char * fname, const char * mode) {
608#ifdef _WIN32
609    FILE * file = NULL;
610
611    // convert fname (UTF-8)
612    wchar_t * wfname = ggml_mbstowcs(fname);
613    if (wfname) {
614        // convert mode (UTF-8)
615        wchar_t * wmode = ggml_mbstowcs(mode);
616        if (wmode) {
617            // open file
618            file = _wfopen(wfname, wmode);
619            GGML_FREE(wmode);
620        }
621
622        GGML_FREE(wfname);
623    }
624
625    return file;
626#else
627    return fopen(fname, mode);
628#endif
629
630}
631
632static const struct ggml_type_traits type_traits[GGML_TYPE_COUNT] = {
633    [GGML_TYPE_I8] = {
634        .type_name                = "i8",
635        .blck_size                = 1,
636        .type_size                = sizeof(int8_t),
637        .is_quantized             = false,
638    },
639    [GGML_TYPE_I16] = {
640        .type_name                = "i16",
641        .blck_size                = 1,
642        .type_size                = sizeof(int16_t),
643        .is_quantized             = false,
644    },
645    [GGML_TYPE_I32] = {
646        .type_name                = "i32",
647        .blck_size                = 1,
648        .type_size                = sizeof(int32_t),
649        .is_quantized             = false,
650    },
651    [GGML_TYPE_I64] = {
652        .type_name                = "i64",
653        .blck_size                = 1,
654        .type_size                = sizeof(int64_t),
655        .is_quantized             = false,
656    },
657    [GGML_TYPE_F64] = {
658        .type_name                = "f64",
659        .blck_size                = 1,
660        .type_size                = sizeof(double),
661        .is_quantized             = false,
662    },
663    [GGML_TYPE_F32] = {
664        .type_name                = "f32",
665        .blck_size                = 1,
666        .type_size                = sizeof(float),
667        .is_quantized             = false,
668    },
669    [GGML_TYPE_F16] = {
670        .type_name                = "f16",
671        .blck_size                = 1,
672        .type_size                = sizeof(ggml_fp16_t),
673        .is_quantized             = false,
674        .to_float                 = (ggml_to_float_t) ggml_fp16_to_fp32_row,
675        .from_float_ref           = (ggml_from_float_t) ggml_fp32_to_fp16_row,
676    },
677    [GGML_TYPE_Q1_0] = {
678        .type_name                = "q1_0",
679        .blck_size                = QK1_0,
680        .type_size                = sizeof(block_q1_0),
681        .is_quantized             = true,
682        .to_float                 = (ggml_to_float_t) dequantize_row_q1_0,
683        .from_float_ref           = (ggml_from_float_t) quantize_row_q1_0_ref,
684    },
685    [GGML_TYPE_Q2_0] = {
686        .type_name                = "q2_0",
687        .blck_size                = QK2_0,
688        .type_size                = sizeof(block_q2_0),
689        .is_quantized             = true,
690        .to_float                 = (ggml_to_float_t) dequantize_row_q2_0,
691        .from_float_ref           = (ggml_from_float_t) quantize_row_q2_0_ref,
692    },
693    [GGML_TYPE_Q4_0] = {
694        .type_name                = "q4_0",
695        .blck_size                = QK4_0,
696        .type_size                = sizeof(block_q4_0),
697        .is_quantized             = true,
698        .to_float                 = (ggml_to_float_t) dequantize_row_q4_0,
699        .from_float_ref           = (ggml_from_float_t) quantize_row_q4_0_ref,
700    },
701    [GGML_TYPE_Q4_1] = {
702        .type_name                = "q4_1",
703        .blck_size                = QK4_1,
704        .type_size                = sizeof(block_q4_1),
705        .is_quantized             = true,
706        .to_float                 = (ggml_to_float_t) dequantize_row_q4_1,
707        .from_float_ref           = (ggml_from_float_t) quantize_row_q4_1_ref,
708    },
709    [4] = { // GGML_TYPE_Q4_2
710        .type_name                = "DEPRECATED",
711        .blck_size                = 0,
712        .type_size                = 0,
713        .is_quantized             = false,
714    },
715    [5] = { // GGML_TYPE_Q4_3
716        .type_name                = "DEPRECATED",
717        .blck_size                = 0,
718        .type_size                = 0,
719        .is_quantized             = false,
720    },
721    [GGML_TYPE_Q5_0] = {
722        .type_name                = "q5_0",
723        .blck_size                = QK5_0,
724        .type_size                = sizeof(block_q5_0),
725        .is_quantized             = true,
726        .to_float                 = (ggml_to_float_t) dequantize_row_q5_0,
727        .from_float_ref           = (ggml_from_float_t) quantize_row_q5_0_ref,
728    },
729    [GGML_TYPE_Q5_1] = {
730        .type_name                = "q5_1",
731        .blck_size                = QK5_1,
732        .type_size                = sizeof(block_q5_1),
733        .is_quantized             = true,
734        .to_float                 = (ggml_to_float_t) dequantize_row_q5_1,
735        .from_float_ref           = (ggml_from_float_t) quantize_row_q5_1_ref,
736    },
737    [GGML_TYPE_Q8_0] = {
738        .type_name                = "q8_0",
739        .blck_size                = QK8_0,
740        .type_size                = sizeof(block_q8_0),
741        .is_quantized             = true,
742        .to_float                 = (ggml_to_float_t) dequantize_row_q8_0,
743        .from_float_ref           = (ggml_from_float_t) quantize_row_q8_0_ref,
744    },
745    [GGML_TYPE_Q8_1] = {
746        .type_name                = "q8_1",
747        .blck_size                = QK8_1,
748        .type_size                = sizeof(block_q8_1),
749        .is_quantized             = true,
750        .from_float_ref           = (ggml_from_float_t) quantize_row_q8_1_ref,
751    },
752    [GGML_TYPE_MXFP4] = {
753        .type_name                = "mxfp4",
754        .blck_size                = QK_MXFP4,
755        .type_size                = sizeof(block_mxfp4),
756        .is_quantized             = true,
757        .to_float                 = (ggml_to_float_t) dequantize_row_mxfp4,
758        .from_float_ref           = (ggml_from_float_t)quantize_row_mxfp4_ref,
759    },
760    [GGML_TYPE_NVFP4] = {
761        .type_name                = "nvfp4",
762        .blck_size                = QK_NVFP4,
763        .type_size                = sizeof(block_nvfp4),
764        .is_quantized             = true,
765        .to_float                 = (ggml_to_float_t) dequantize_row_nvfp4,
766        .from_float_ref           = (ggml_from_float_t)quantize_row_nvfp4_ref,
767    },
768    [GGML_TYPE_Q2_K] = {
769        .type_name                = "q2_K",
770        .blck_size                = QK_K,
771        .type_size                = sizeof(block_q2_K),
772        .is_quantized             = true,
773        .to_float                 = (ggml_to_float_t) dequantize_row_q2_K,
774        .from_float_ref           = (ggml_from_float_t) quantize_row_q2_K_ref,
775    },
776    [GGML_TYPE_Q3_K] = {
777        .type_name                = "q3_K",
778        .blck_size                = QK_K,
779        .type_size                = sizeof(block_q3_K),
780        .is_quantized             = true,
781        .to_float                 = (ggml_to_float_t) dequantize_row_q3_K,
782        .from_float_ref           = (ggml_from_float_t) quantize_row_q3_K_ref,
783    },
784    [GGML_TYPE_Q4_K] = {
785        .type_name                = "q4_K",
786        .blck_size                = QK_K,
787        .type_size                = sizeof(block_q4_K),
788        .is_quantized             = true,
789        .to_float                 = (ggml_to_float_t) dequantize_row_q4_K,
790        .from_float_ref           = (ggml_from_float_t) quantize_row_q4_K_ref,
791    },
792    [GGML_TYPE_Q5_K] = {
793        .type_name                = "q5_K",
794        .blck_size                = QK_K,
795        .type_size                = sizeof(block_q5_K),
796        .is_quantized             = true,
797        .to_float                 = (ggml_to_float_t) dequantize_row_q5_K,
798        .from_float_ref           = (ggml_from_float_t) quantize_row_q5_K_ref,
799    },
800    [GGML_TYPE_Q6_K] = {
801        .type_name                = "q6_K",
802        .blck_size                = QK_K,
803        .type_size                = sizeof(block_q6_K),
804        .is_quantized             = true,
805        .to_float                 = (ggml_to_float_t) dequantize_row_q6_K,
806        .from_float_ref           = (ggml_from_float_t) quantize_row_q6_K_ref,
807    },
808    [GGML_TYPE_IQ2_XXS] = {
809        .type_name                = "iq2_xxs",
810        .blck_size                = QK_K,
811        .type_size                = sizeof(block_iq2_xxs),
812        .is_quantized             = true,
813        .to_float                 = (ggml_to_float_t) dequantize_row_iq2_xxs,
814        .from_float_ref           = NULL,
815    },
816    [GGML_TYPE_IQ2_XS] = {
817        .type_name                = "iq2_xs",
818        .blck_size                = QK_K,
819        .type_size                = sizeof(block_iq2_xs),
820        .is_quantized             = true,
821        .to_float                 = (ggml_to_float_t) dequantize_row_iq2_xs,
822        .from_float_ref           = NULL,
823    },
824    [GGML_TYPE_IQ3_XXS] = {
825        .type_name                = "iq3_xxs",
826        .blck_size                = QK_K,
827        .type_size                = sizeof(block_iq3_xxs),
828        .is_quantized             = true,
829        .to_float                 = (ggml_to_float_t) dequantize_row_iq3_xxs,
830        .from_float_ref           = (ggml_from_float_t)quantize_row_iq3_xxs_ref,
831    },
832    [GGML_TYPE_IQ3_S] = {
833        .type_name                = "iq3_s",
834        .blck_size                = QK_K,
835        .type_size                = sizeof(block_iq3_s),
836        .is_quantized             = true,
837        .to_float                 = (ggml_to_float_t) dequantize_row_iq3_s,
838        .from_float_ref           = (ggml_from_float_t)quantize_row_iq3_s_ref,
839    },
840    [GGML_TYPE_IQ2_S] = {
841        .type_name                = "iq2_s",
842        .blck_size                = QK_K,
843        .type_size                = sizeof(block_iq2_s),
844        .is_quantized             = true,
845        .to_float                 = (ggml_to_float_t) dequantize_row_iq2_s,
846        .from_float_ref           = (ggml_from_float_t)quantize_row_iq2_s_ref,
847    },
848    [GGML_TYPE_IQ1_S] = {
849        .type_name                = "iq1_s",
850        .blck_size                = QK_K,
851        .type_size                = sizeof(block_iq1_s),
852        .is_quantized             = true,
853        .to_float                 = (ggml_to_float_t) dequantize_row_iq1_s,
854        .from_float_ref           = NULL,
855    },
856    [GGML_TYPE_IQ1_M] = {
857        .type_name                = "iq1_m",
858        .blck_size                = QK_K,
859        .type_size                = sizeof(block_iq1_m),
860        .is_quantized             = true,
861        .to_float                 = (ggml_to_float_t) dequantize_row_iq1_m,
862        .from_float_ref           = NULL,
863    },
864    [GGML_TYPE_IQ4_NL] = {
865        .type_name                = "iq4_nl",
866        .blck_size                = QK4_NL,
867        .type_size                = sizeof(block_iq4_nl),
868        .is_quantized             = true,
869        .to_float                 = (ggml_to_float_t) dequantize_row_iq4_nl,
870        .from_float_ref           = (ggml_from_float_t)quantize_row_iq4_nl_ref,
871    },
872    [GGML_TYPE_IQ4_XS] = {
873        .type_name                = "iq4_xs",
874        .blck_size                = QK_K,
875        .type_size                = sizeof(block_iq4_xs),
876        .is_quantized             = true,
877        .to_float                 = (ggml_to_float_t) dequantize_row_iq4_xs,
878        .from_float_ref           = (ggml_from_float_t)quantize_row_iq4_xs_ref,
879    },
880    [GGML_TYPE_Q8_K] = {
881        .type_name                = "q8_K",
882        .blck_size                = QK_K,
883        .type_size                = sizeof(block_q8_K),
884        .is_quantized             = true,
885    },
886    [GGML_TYPE_BF16] = {
887        .type_name                = "bf16",
888        .blck_size                = 1,
889        .type_size                = sizeof(ggml_bf16_t),
890        .is_quantized             = false,
891        .to_float                 = (ggml_to_float_t) ggml_bf16_to_fp32_row,
892        .from_float_ref           = (ggml_from_float_t) ggml_fp32_to_bf16_row_ref,
893    },
894    [31] = { // GGML_TYPE_Q4_0_4_4
895        .type_name                = "TYPE_Q4_0_4_4 REMOVED, use Q4_0 with runtime repacking",
896        .blck_size                = 0,
897        .type_size                = 0,
898        .is_quantized             = false,
899    },
900    [32] = { // GGML_TYPE_Q4_0_4_8
901        .type_name                = "TYPE_Q4_0_4_8 REMOVED, use Q4_0 with runtime repacking",
902        .blck_size                = 0,
903        .type_size                = 0,
904        .is_quantized             = false,
905    },
906    [33] = { // GGML_TYPE_Q4_0_8_8
907        .type_name                = "TYPE_Q4_0_8_8 REMOVED, use Q4_0 with runtime repacking",
908        .blck_size                = 0,
909        .type_size                = 0,
910        .is_quantized             = false,
911    },
912    [GGML_TYPE_TQ1_0] = {
913        .type_name                = "tq1_0",
914        .blck_size                = QK_K,
915        .type_size                = sizeof(block_tq1_0),
916        .is_quantized             = true,
917        .to_float                 = (ggml_to_float_t) dequantize_row_tq1_0,
918        .from_float_ref           = (ggml_from_float_t) quantize_row_tq1_0_ref,
919    },
920    [GGML_TYPE_TQ2_0] = {
921        .type_name                = "tq2_0",
922        .blck_size                = QK_K,
923        .type_size                = sizeof(block_tq2_0),
924        .is_quantized             = true,
925        .to_float                 = (ggml_to_float_t) dequantize_row_tq2_0,
926        .from_float_ref           = (ggml_from_float_t) quantize_row_tq2_0_ref,
927    },
928    [36] = { // GGML_TYPE_IQ4_NL_4_4
929        .type_name                = "TYPE_IQ4_NL_4_4 REMOVED, use IQ4_NL with runtime repacking",
930        .blck_size                = 0,
931        .type_size                = 0,
932        .is_quantized             = false,
933    },
934    [37] = { // GGML_TYPE_IQ4_NL_4_8
935        .type_name                = "TYPE_IQ4_NL_4_8 REMOVED, use IQ4_NL with runtime repacking",
936        .blck_size                = 0,
937        .type_size                = 0,
938        .is_quantized             = false,
939    },
940    [38] = { // GGML_TYPE_IQ4_NL_8_8
941        .type_name                = "TYPE_IQ4_NL_8_8 REMOVED, use IQ4_NL with runtime repacking",
942        .blck_size                = 0,
943        .type_size                = 0,
944        .is_quantized             = false,
945    },
946};
947
948const struct ggml_type_traits * ggml_get_type_traits(enum ggml_type type) {
949    assert(type >= 0);
950    assert(type < GGML_TYPE_COUNT);
951    return &type_traits[type];
952}
953
954//
955// ggml object
956//
957
958struct ggml_object {
959    size_t offs;
960    size_t size;
961
962    struct ggml_object * next;
963
964    enum ggml_object_type type;
965
966    char padding[4];
967};
968
969static const size_t GGML_OBJECT_SIZE = sizeof(struct ggml_object);
970
971//
972// ggml context
973//
974
975struct ggml_context {
976    size_t mem_size;
977    void * mem_buffer;
978    bool   mem_buffer_owned;
979    bool   no_alloc;
980
981    int    n_objects;
982
983    struct ggml_object * objects_begin;
984    struct ggml_object * objects_end;
985};
986
987//
988// data types
989//
990
991static const char * GGML_OP_NAME[GGML_OP_COUNT] = {
992    "NONE",
993
994    "DUP",
995    "ADD",
996    "ADD_ID",
997    "ADD1",
998    "ACC",
999    "SUB",
1000    "MUL",
1001    "DIV",
1002    "SQR",
1003    "SQRT",
1004    "LOG",
1005    "SIN",
1006    "COS",
1007    "SUM",
1008    "SUM_ROWS",
1009    "CUMSUM",
1010    "MEAN",
1011    "ARGMAX",
1012    "COUNT_EQUAL",
1013    "REPEAT",
1014    "REPEAT_BACK",
1015    "CONCAT",
1016    "SILU_BACK",
1017    "NORM",
1018    "RMS_NORM",
1019    "RMS_NORM_BACK",
1020    "GROUP_NORM",
1021    "L2_NORM",
1022
1023    "MUL_MAT",
1024    "MUL_MAT_ID",
1025    "OUT_PROD",
1026
1027    "SCALE",
1028    "SET",
1029    "CPY",
1030    "CONT",
1031    "RESHAPE",
1032    "VIEW",
1033    "PERMUTE",
1034    "TRANSPOSE",
1035    "GET_ROWS",
1036    "GET_ROWS_BACK",
1037    "SET_ROWS",
1038    "DIAG",
1039    "DIAG_MASK_INF",
1040    "DIAG_MASK_ZERO",
1041    "SOFT_MAX",
1042    "SOFT_MAX_BACK",
1043    "ROPE",
1044    "ROPE_BACK",
1045    "CLAMP",
1046    "CONV_TRANSPOSE_1D",
1047    "IM2COL",
1048    "IM2COL_BACK",
1049    "IM2COL_3D",
1050    "COL2IM_1D",
1051    "CONV_2D",
1052    "CONV_3D",
1053    "CONV_2D_DW",
1054    "CONV_TRANSPOSE_2D",
1055    "POOL_1D",
1056    "POOL_2D",
1057    "POOL_2D_BACK",
1058    "UPSCALE",
1059    "PAD",
1060    "PAD_REFLECT_1D",
1061    "ROLL",
1062    "ARANGE",
1063    "TIMESTEP_EMBEDDING",
1064    "ARGSORT",
1065    "TOP_K",
1066    "LEAKY_RELU",
1067    "TRI",
1068    "FILL",
1069
1070    "FLASH_ATTN_EXT",
1071    "FLASH_ATTN_BACK",
1072    "SSM_CONV",
1073    "SSM_SCAN",
1074    "WIN_PART",
1075    "WIN_UNPART",
1076    "GET_REL_POS",
1077    "ADD_REL_POS",
1078    "RWKV_WKV6",
1079    "GATED_LINEAR_ATTN",
1080    "RWKV_WKV7",
1081    "SOLVE_TRI",
1082    "GATED_DELTA_NET",
1083    "LIGHTNING_INDEXER",
1084    "DSV4_HC_COMB",
1085    "DSV4_HC_PRE",
1086    "DSV4_HC_POST",
1087
1088    "UNARY",
1089
1090    "MAP_CUSTOM1",
1091    "MAP_CUSTOM2",
1092    "MAP_CUSTOM3",
1093
1094    "CUSTOM",
1095
1096    "CROSS_ENTROPY_LOSS",
1097    "CROSS_ENTROPY_LOSS_BACK",
1098    "OPT_STEP_ADAMW",
1099    "OPT_STEP_SGD",
1100
1101    "GLU",
1102};
1103
1104static_assert(GGML_OP_COUNT == 101, "GGML_OP_COUNT != 101");
1105
1106static const char * GGML_OP_SYMBOL[GGML_OP_COUNT] = {
1107    "none",
1108
1109    "x",
1110    "x+y",
1111    "x[i]+y",
1112    "x+y",
1113    "view(x,nb,offset)+=y->x",
1114    "x-y",
1115    "x*y",
1116    "x/y",
1117    "x^2",
1118    "√x",
1119    "log(x)",
1120    "sin(x)",
1121    "cos(x)",
1122    "Σx",
1123    "Σx_k",
1124    "cumsum(x)",
1125    "Σx/n",
1126    "argmax(x)",
1127    "count_equal(x)",
1128    "repeat(x)",
1129    "repeat_back(x)",
1130    "concat(x, y)",
1131    "silu_back(x)",
1132    "norm(x)",
1133    "rms_norm(x)",
1134    "rms_norm_back(x)",
1135    "group_norm(x)",
1136    "l2_norm(x)",
1137
1138    "X*Y",
1139    "X[i]*Y",
1140    "X*Y",
1141
1142    "x*v",
1143    "y-\\>view(x)",
1144    "x-\\>y",
1145    "cont(x)",
1146    "reshape(x)",
1147    "view(x)",
1148    "permute(x)",
1149    "transpose(x)",
1150    "get_rows(x)",
1151    "get_rows_back(x)",
1152    "set_rows(x)",
1153    "diag(x)",
1154    "diag_mask_inf(x)",
1155    "diag_mask_zero(x)",
1156    "soft_max(x)",
1157    "soft_max_back(x)",
1158    "rope(x)",
1159    "rope_back(x)",
1160    "clamp(x)",
1161    "conv_transpose_1d(x)",
1162    "im2col(x)",
1163    "im2col_back(x)",
1164    "im2col_3d(x)",
1165    "col2im_1d(x)",
1166    "conv_2d(x)",
1167    "conv_3d(x)",
1168    "conv_2d_dw(x)",
1169    "conv_transpose_2d(x)",
1170    "pool_1d(x)",
1171    "pool_2d(x)",
1172    "pool_2d_back(x)",
1173    "upscale(x)",
1174    "pad(x)",
1175    "pad_reflect_1d(x)",
1176    "roll(x)",
1177    "arange(start, stop, step)",
1178    "timestep_embedding(timesteps, dim, max_period)",
1179    "argsort(x)",
1180    "top_k(x)",
1181    "leaky_relu(x)",
1182    "tri(x)",
1183    "fill(x, c)",
1184
1185    "flash_attn_ext(x)",
1186    "flash_attn_back(x)",
1187    "ssm_conv(x)",
1188    "ssm_scan(x)",
1189    "win_part(x)",
1190    "win_unpart(x)",
1191    "get_rel_pos(x)",
1192    "add_rel_pos(x)",
1193    "rwkv_wkv6(k, v, r, tf, td, s)",
1194    "gated_linear_attn(k, v, q, gate, s)",
1195    "rwkv_wkv7(r, w, k, v, a, b, s)",
1196    "A X = B, A triangular, solve X",
1197    "gated_delta_net(q, k, v, g, beta, s)",
1198    "lightning_indexer(q, k, weights, mask)",
1199    "dsv4_hc_comb(mixes, scale, base)",
1200    "dsv4_hc_pre(x, weights)",
1201    "dsv4_hc_post(x, residual, post, comb)",
1202
1203    "unary(x)",
1204
1205    "map_custom(x)",
1206    "map_custom(x,y)",
1207    "map_custom(x,y,z)",
1208
1209    "custom(x)",
1210
1211    "cross_entropy_loss(x,y)",
1212    "cross_entropy_loss_back(x,y)",
1213    "adamw(x)",
1214    "sgd(x)",
1215
1216    "glu(x)",
1217};
1218
1219static_assert(GGML_OP_COUNT == 101, "GGML_OP_COUNT != 101");
1220
1221static_assert(GGML_OP_POOL_COUNT == 2, "GGML_OP_POOL_COUNT != 2");
1222
1223static const char * GGML_UNARY_OP_NAME[GGML_UNARY_OP_COUNT] = {
1224    "ABS",
1225    "SGN",
1226    "NEG",
1227    "STEP",
1228    "TANH",
1229    "ELU",
1230    "RELU",
1231    "SIGMOID",
1232    "GELU",
1233    "GELU_QUICK",
1234    "SILU",
1235    "HARDSWISH",
1236    "HARDSIGMOID",
1237    "EXP",
1238    "EXPM1",
1239    "SOFTPLUS",
1240    "GELU_ERF",
1241    "XIELU",
1242    "FLOOR",
1243    "CEIL",
1244    "ROUND",
1245    "TRUNC",
1246};
1247
1248static_assert(GGML_UNARY_OP_COUNT == 22, "GGML_UNARY_OP_COUNT != 22");
1249
1250static const char * GGML_GLU_OP_NAME[GGML_GLU_OP_COUNT] = {
1251    "REGLU",
1252    "GEGLU",
1253    "SWIGLU",
1254    "SWIGLU_OAI",
1255    "GEGLU_ERF",
1256    "GEGLU_QUICK",
1257    "SWIGLU_CLAMP",
1258};
1259
1260static_assert(GGML_GLU_OP_COUNT == 7, "GGML_GLU_OP_COUNT != 7");
1261
1262static_assert(sizeof(struct ggml_object)%GGML_MEM_ALIGN == 0, "ggml_object size must be a multiple of GGML_MEM_ALIGN");
1263static_assert(sizeof(struct ggml_tensor)%GGML_MEM_ALIGN == 0, "ggml_tensor size must be a multiple of GGML_MEM_ALIGN");
1264
1265
1266////////////////////////////////////////////////////////////////////////////////
1267
1268void ggml_print_object(const struct ggml_object * obj) {
1269    GGML_LOG_INFO(" - ggml_object: type = %d, offset = %zu, size = %zu, next = %p\n",
1270            obj->type, obj->offs, obj->size, (const void *) obj->next);
1271}
1272
1273void ggml_print_objects(const struct ggml_context * ctx) {
1274    struct ggml_object * obj = ctx->objects_begin;
1275
1276    GGML_LOG_INFO("%s: objects in context %p:\n", __func__, (const void *) ctx);
1277
1278    while (obj != NULL) {
1279        ggml_print_object(obj);
1280        obj = obj->next;
1281    }
1282
1283    GGML_LOG_INFO("%s: --- end ---\n", __func__);
1284}
1285
1286int64_t ggml_nelements(const struct ggml_tensor * tensor) {
1287    static_assert(GGML_MAX_DIMS == 4, "GGML_MAX_DIMS is not 4 - update this function");
1288
1289    return tensor->ne[0]*tensor->ne[1]*tensor->ne[2]*tensor->ne[3];
1290}
1291
1292int64_t ggml_nrows(const struct ggml_tensor * tensor) {
1293    static_assert(GGML_MAX_DIMS == 4, "GGML_MAX_DIMS is not 4 - update this function");
1294
1295    return tensor->ne[1]*tensor->ne[2]*tensor->ne[3];
1296}
1297
1298size_t ggml_nbytes(const struct ggml_tensor * tensor) {
1299    for (int i = 0; i < GGML_MAX_DIMS; ++i) {
1300        if (tensor->ne[i] <= 0) {
1301            return 0;
1302        }
1303    }
1304
1305    size_t nbytes;
1306    const size_t blck_size = ggml_blck_size(tensor->type);
1307    if (blck_size == 1) {
1308        nbytes = ggml_type_size(tensor->type);
1309        for (int i = 0; i < GGML_MAX_DIMS; ++i) {
1310            nbytes += (tensor->ne[i] - 1)*tensor->nb[i];
1311        }
1312    }
1313    else {
1314        nbytes = tensor->ne[0]*tensor->nb[0]/blck_size;
1315        for (int i = 1; i < GGML_MAX_DIMS; ++i) {
1316            nbytes += (tensor->ne[i] - 1)*tensor->nb[i];
1317        }
1318    }
1319
1320    return nbytes;
1321}
1322
1323size_t ggml_nbytes_pad(const struct ggml_tensor * tensor) {
1324    return GGML_PAD(ggml_nbytes(tensor), GGML_MEM_ALIGN);
1325}
1326
1327int64_t ggml_blck_size(enum ggml_type type) {
1328    assert(type >= 0);
1329    assert(type < GGML_TYPE_COUNT);
1330    return type_traits[type].blck_size;
1331}
1332
1333size_t ggml_type_size(enum ggml_type type) {
1334    assert(type >= 0);
1335    assert(type < GGML_TYPE_COUNT);
1336    return type_traits[type].type_size;
1337}
1338
1339size_t ggml_row_size(enum ggml_type type, int64_t ne) {
1340    assert(type >= 0);
1341    assert(type < GGML_TYPE_COUNT);
1342    assert(ne % ggml_blck_size(type) == 0);
1343    return ggml_type_size(type)*ne/ggml_blck_size(type);
1344}
1345
1346double ggml_type_sizef(enum ggml_type type) {
1347    assert(type >= 0);
1348    assert(type < GGML_TYPE_COUNT);
1349    return ((double)(type_traits[type].type_size))/type_traits[type].blck_size;
1350}
1351
1352const char * ggml_type_name(enum ggml_type type) {
1353    assert(type >= 0);
1354    assert(type < GGML_TYPE_COUNT);
1355    return type_traits[type].type_name;
1356}
1357
1358bool ggml_is_quantized(enum ggml_type type) {
1359    assert(type >= 0);
1360    assert(type < GGML_TYPE_COUNT);
1361    return type_traits[type].is_quantized;
1362}
1363
1364const char * ggml_op_name(enum ggml_op op) {
1365    return GGML_OP_NAME[op];
1366}
1367
1368const char * ggml_op_symbol(enum ggml_op op) {
1369    return GGML_OP_SYMBOL[op];
1370}
1371
1372const char * ggml_unary_op_name(enum ggml_unary_op op) {
1373    return GGML_UNARY_OP_NAME[op];
1374}
1375
1376const char * ggml_glu_op_name(enum ggml_glu_op op) {
1377    return GGML_GLU_OP_NAME[op];
1378}
1379
1380const char * ggml_op_desc(const struct ggml_tensor * t) {
1381    if (t->op == GGML_OP_UNARY) {
1382        enum ggml_unary_op uop = ggml_get_unary_op(t);
1383        return ggml_unary_op_name(uop);
1384    }
1385    if (t->op == GGML_OP_GLU) {
1386        enum ggml_glu_op gop = ggml_get_glu_op(t);
1387        return ggml_glu_op_name(gop);
1388    }
1389    return ggml_op_name(t->op);
1390}
1391
1392size_t ggml_element_size(const struct ggml_tensor * tensor) {
1393    return ggml_type_size(tensor->type);
1394}
1395
1396bool ggml_is_scalar(const struct ggml_tensor * tensor) {
1397    static_assert(GGML_MAX_DIMS == 4, "GGML_MAX_DIMS is not 4 - update this function");
1398
1399    return tensor->ne[0] == 1 && tensor->ne[1] == 1 && tensor->ne[2] == 1 && tensor->ne[3] == 1;
1400}
1401
1402bool ggml_is_vector(const struct ggml_tensor * tensor) {
1403    static_assert(GGML_MAX_DIMS == 4, "GGML_MAX_DIMS is not 4 - update this function");
1404
1405    return tensor->ne[1] == 1 && tensor->ne[2] == 1 && tensor->ne[3] == 1;
1406}
1407
1408bool ggml_is_matrix(const struct ggml_tensor * tensor) {
1409    static_assert(GGML_MAX_DIMS == 4, "GGML_MAX_DIMS is not 4 - update this function");
1410
1411    return tensor->ne[2] == 1 && tensor->ne[3] == 1;
1412}
1413
1414bool ggml_is_3d(const struct ggml_tensor * tensor) {
1415    return tensor->ne[3] == 1;
1416}
1417
1418int ggml_n_dims(const struct ggml_tensor * tensor) {
1419    for (int i = GGML_MAX_DIMS - 1; i >= 1; --i) {
1420        if (tensor->ne[i] > 1) {
1421            return i + 1;
1422        }
1423    }
1424    return 1;
1425}
1426
1427enum ggml_type ggml_ftype_to_ggml_type(enum ggml_ftype ftype) {
1428    enum ggml_type wtype = GGML_TYPE_COUNT;
1429
1430    switch (ftype) {
1431        case GGML_FTYPE_ALL_F32:              wtype = GGML_TYPE_F32;   break;
1432        case GGML_FTYPE_MOSTLY_F16:           wtype = GGML_TYPE_F16;   break;
1433        case GGML_FTYPE_MOSTLY_BF16:          wtype = GGML_TYPE_BF16;  break;
1434        case GGML_FTYPE_MOSTLY_Q4_0:          wtype = GGML_TYPE_Q4_0;  break;
1435        case GGML_FTYPE_MOSTLY_Q4_1:          wtype = GGML_TYPE_Q4_1;  break;
1436        case GGML_FTYPE_MOSTLY_Q1_0:          wtype = GGML_TYPE_Q1_0;  break;
1437        case GGML_FTYPE_MOSTLY_Q2_0:          wtype = GGML_TYPE_Q2_0;  break;
1438        case GGML_FTYPE_MOSTLY_Q5_0:          wtype = GGML_TYPE_Q5_0;  break;
1439        case GGML_FTYPE_MOSTLY_Q5_1:          wtype = GGML_TYPE_Q5_1;  break;
1440        case GGML_FTYPE_MOSTLY_Q8_0:          wtype = GGML_TYPE_Q8_0;  break;
1441        case GGML_FTYPE_MOSTLY_MXFP4:         wtype = GGML_TYPE_MXFP4; break;
1442        case GGML_FTYPE_MOSTLY_NVFP4:         wtype = GGML_TYPE_NVFP4; break;
1443        case GGML_FTYPE_MOSTLY_Q2_K:          wtype = GGML_TYPE_Q2_K;  break;
1444        case GGML_FTYPE_MOSTLY_Q3_K:          wtype = GGML_TYPE_Q3_K;  break;
1445        case GGML_FTYPE_MOSTLY_Q4_K:          wtype = GGML_TYPE_Q4_K;  break;
1446        case GGML_FTYPE_MOSTLY_Q5_K:          wtype = GGML_TYPE_Q5_K;  break;
1447        case GGML_FTYPE_MOSTLY_Q6_K:          wtype = GGML_TYPE_Q6_K;  break;
1448        case GGML_FTYPE_MOSTLY_IQ2_XXS:       wtype = GGML_TYPE_IQ2_XXS;  break;
1449        case GGML_FTYPE_MOSTLY_IQ2_XS:        wtype = GGML_TYPE_IQ2_XS;   break;
1450        case GGML_FTYPE_MOSTLY_IQ3_XXS:       wtype = GGML_TYPE_IQ3_XXS;  break;
1451        case GGML_FTYPE_MOSTLY_IQ1_S:         wtype = GGML_TYPE_IQ1_S;    break;
1452        case GGML_FTYPE_MOSTLY_IQ1_M:         wtype = GGML_TYPE_IQ1_M;    break;
1453        case GGML_FTYPE_MOSTLY_IQ4_NL:        wtype = GGML_TYPE_IQ4_NL;   break;
1454        case GGML_FTYPE_MOSTLY_IQ4_XS:        wtype = GGML_TYPE_IQ4_XS;   break;
1455        case GGML_FTYPE_MOSTLY_IQ3_S:         wtype = GGML_TYPE_IQ3_S;    break;
1456        case GGML_FTYPE_MOSTLY_IQ2_S:         wtype = GGML_TYPE_IQ2_S;    break;
1457        case GGML_FTYPE_UNKNOWN:              wtype = GGML_TYPE_COUNT; break;
1458        case GGML_FTYPE_MOSTLY_Q4_1_SOME_F16: wtype = GGML_TYPE_COUNT; break;
1459    }
1460
1461    GGML_ASSERT(wtype != GGML_TYPE_COUNT);
1462
1463    return wtype;
1464}
1465
1466size_t ggml_tensor_overhead(void) {
1467    return GGML_OBJECT_SIZE + GGML_TENSOR_SIZE;
1468}
1469
1470bool ggml_is_transposed(const struct ggml_tensor * tensor) {
1471    return tensor->nb[0] > tensor->nb[1];
1472}
1473
1474static bool ggml_is_contiguous_m_n(const struct ggml_tensor * tensor, int m, int n) {
1475    size_t next_nb = ggml_type_size(tensor->type);
1476    if (tensor->ne[0] != ggml_blck_size(tensor->type) && tensor->nb[0] != next_nb) {
1477        return false;
1478    }
1479    next_nb *= tensor->ne[0]/ggml_blck_size(tensor->type);
1480    for (int i = 1; i < n; i++) {
1481        if (i > m) {
1482            if (tensor->ne[i] != 1 && tensor->nb[i] != next_nb) {
1483                return false;
1484            }
1485            next_nb *= tensor->ne[i];
1486        } else {
1487            // this dimension does not need to be contiguous
1488            next_nb = tensor->ne[i]*tensor->nb[i];
1489        }
1490    }
1491    return true;
1492}
1493
1494bool ggml_is_contiguous(const struct ggml_tensor * tensor) {
1495    return ggml_is_contiguous_0(tensor);
1496}
1497
1498bool ggml_is_contiguous_0(const struct ggml_tensor * tensor) {
1499    return ggml_is_contiguous_m_n(tensor, 0, GGML_MAX_DIMS);
1500}
1501
1502bool ggml_is_contiguous_1(const struct ggml_tensor * tensor) {
1503    return ggml_is_contiguous_m_n(tensor, 1, GGML_MAX_DIMS);
1504}
1505
1506bool ggml_is_contiguous_2(const struct ggml_tensor * tensor) {
1507    return ggml_is_contiguous_m_n(tensor, 2, GGML_MAX_DIMS);
1508}
1509
1510bool ggml_is_contiguous_to_1(const struct ggml_tensor * tensor) {
1511    return ggml_is_contiguous_m_n(tensor, 0, 1);
1512}
1513
1514bool ggml_is_contiguous_to_2(const struct ggml_tensor * tensor) {
1515    return ggml_is_contiguous_m_n(tensor, 0, 2);
1516}
1517
1518bool ggml_is_contiguous_to_3(const struct ggml_tensor * tensor) {
1519    return ggml_is_contiguous_m_n(tensor, 0, 3);
1520}
1521
1522bool ggml_is_contiguously_allocated(const struct ggml_tensor * tensor) {
1523    return ggml_nbytes(tensor) == ggml_nelements(tensor) * ggml_type_size(tensor->type)/ggml_blck_size(tensor->type);
1524}
1525
1526bool ggml_is_permuted(const struct ggml_tensor * tensor) {
1527    static_assert(GGML_MAX_DIMS == 4, "GGML_MAX_DIMS is not 4 - update this function");
1528
1529    return tensor->nb[0] > tensor->nb[1] || tensor->nb[1] > tensor->nb[2] || tensor->nb[2] > tensor->nb[3];
1530}
1531
1532bool ggml_is_contiguous_channels(const struct ggml_tensor * tensor) {
1533    return
1534        tensor->nb[0] > tensor->nb[2] &&
1535        tensor->nb[1] > tensor->nb[0] &&
1536        tensor->nb[2] == ggml_type_size(tensor->type);
1537}
1538
1539bool ggml_is_contiguous_rows(const struct ggml_tensor * tensor) {
1540    return
1541        tensor->ne[0] == ggml_blck_size(tensor->type) ||
1542        tensor->nb[0] == ggml_type_size(tensor->type);
1543}
1544
1545static inline bool ggml_is_padded_1d(const struct ggml_tensor * tensor) {
1546    static_assert(GGML_MAX_DIMS == 4, "GGML_MAX_DIMS is not 4 - update this function");
1547
1548    return
1549        tensor->nb[0] == ggml_type_size(tensor->type) &&
1550        tensor->nb[2] == tensor->nb[1]*tensor->ne[1] &&
1551        tensor->nb[3] == tensor->nb[2]*tensor->ne[2];
1552}
1553
1554bool ggml_is_empty(const struct ggml_tensor * tensor) {
1555    for (int i = 0; i < GGML_MAX_DIMS; ++i) {
1556        if (tensor->ne[i] == 0) {
1557            // empty if any dimension has no elements
1558            return true;
1559        }
1560    }
1561    return false;
1562}
1563
1564bool ggml_are_same_shape(const struct ggml_tensor * t0, const struct ggml_tensor * t1) {
1565    static_assert(GGML_MAX_DIMS == 4, "GGML_MAX_DIMS is not 4 - update this function");
1566
1567    return
1568        (t0->ne[0] == t1->ne[0]) &&
1569        (t0->ne[1] == t1->ne[1]) &&
1570        (t0->ne[2] == t1->ne[2]) &&
1571        (t0->ne[3] == t1->ne[3]);
1572}
1573
1574bool ggml_are_same_stride(const struct ggml_tensor * t0, const struct ggml_tensor * t1) {
1575    static_assert(GGML_MAX_DIMS == 4, "GGML_MAX_DIMS is not 4 - update this function");
1576
1577    return
1578        (t0->nb[0] == t1->nb[0]) &&
1579        (t0->nb[1] == t1->nb[1]) &&
1580        (t0->nb[2] == t1->nb[2]) &&
1581        (t0->nb[3] == t1->nb[3]);
1582}
1583
1584bool ggml_is_view(const struct ggml_tensor * t) {
1585    return ggml_impl_is_view(t);
1586}
1587
1588// check if t1 can be represented as a repetition of t0
1589bool ggml_can_repeat(const struct ggml_tensor * t0, const struct ggml_tensor * t1) {
1590    static_assert(GGML_MAX_DIMS == 4, "GGML_MAX_DIMS is not 4 - update this function");
1591
1592    return ggml_is_empty(t0) ? ggml_is_empty(t1) :
1593        (t1->ne[0]%t0->ne[0] == 0) &&
1594        (t1->ne[1]%t0->ne[1] == 0) &&
1595        (t1->ne[2]%t0->ne[2] == 0) &&
1596        (t1->ne[3]%t0->ne[3] == 0);
1597}
1598
1599static inline bool ggml_can_repeat_rows(const struct ggml_tensor * t0, const struct ggml_tensor * t1) {
1600    static_assert(GGML_MAX_DIMS == 4, "GGML_MAX_DIMS is not 4 - update this function");
1601
1602    return (t0->ne[0] == t1->ne[0]) && ggml_can_repeat(t0, t1);
1603}
1604
1605// assert that pointer is aligned to GGML_MEM_ALIGN
1606#define GGML_ASSERT_ALIGNED(ptr) \
1607    GGML_ASSERT(((uintptr_t) (ptr))%GGML_MEM_ALIGN == 0)
1608
1609////////////////////////////////////////////////////////////////////////////////
1610
1611struct ggml_context * ggml_init(struct ggml_init_params params) {
1612    static bool is_first_call = true;
1613
1614    ggml_critical_section_start();
1615
1616    if (is_first_call) {
1617        // initialize time system (required on Windows)
1618        ggml_time_init();
1619
1620        is_first_call = false;
1621    }
1622
1623    ggml_critical_section_end();
1624
1625    struct ggml_context * ctx = GGML_MALLOC(sizeof(struct ggml_context));
1626
1627    // allow to call ggml_init with 0 size
1628    if (params.mem_size == 0) {
1629        params.mem_size = GGML_MEM_ALIGN;
1630    }
1631
1632    const size_t mem_size = params.mem_buffer ? params.mem_size : GGML_PAD(params.mem_size, GGML_MEM_ALIGN);
1633
1634    *ctx = (struct ggml_context) {
1635        /*.mem_size           =*/ mem_size,
1636        /*.mem_buffer         =*/ params.mem_buffer ? params.mem_buffer : ggml_aligned_malloc(mem_size),
1637        /*.mem_buffer_owned   =*/ params.mem_buffer ? false : true,
1638        /*.no_alloc           =*/ params.no_alloc,
1639        /*.n_objects          =*/ 0,
1640        /*.objects_begin      =*/ NULL,
1641        /*.objects_end        =*/ NULL,
1642    };
1643
1644    GGML_ASSERT(ctx->mem_buffer != NULL);
1645
1646    GGML_ASSERT_ALIGNED(ctx->mem_buffer);
1647
1648    GGML_PRINT_DEBUG("%s: context initialized\n", __func__);
1649
1650    return ctx;
1651}
1652
1653void ggml_reset(struct ggml_context * ctx) {
1654    if (ctx == NULL) {
1655        return;
1656    }
1657
1658    ctx->n_objects     = 0;
1659    ctx->objects_begin = NULL;
1660    ctx->objects_end   = NULL;
1661}
1662
1663void ggml_free(struct ggml_context * ctx) {
1664    if (ctx == NULL) {
1665        return;
1666    }
1667
1668    if (ctx->mem_buffer_owned) {
1669        ggml_aligned_free(ctx->mem_buffer, ctx->mem_size);
1670    }
1671
1672    GGML_FREE(ctx);
1673}
1674
1675size_t ggml_used_mem(const struct ggml_context * ctx) {
1676    return ctx->objects_end == NULL ? 0 : ctx->objects_end->offs + ctx->objects_end->size;
1677}
1678
1679bool ggml_get_no_alloc(struct ggml_context * ctx) {
1680    return ctx->no_alloc;
1681}
1682
1683void ggml_set_no_alloc(struct ggml_context * ctx, bool no_alloc) {
1684    ctx->no_alloc = no_alloc;
1685}
1686
1687void * ggml_get_mem_buffer(const struct ggml_context * ctx) {
1688    return ctx->mem_buffer;
1689}
1690
1691size_t ggml_get_mem_size(const struct ggml_context * ctx) {
1692    return ctx->mem_size;
1693}
1694
1695size_t ggml_get_max_tensor_size(const struct ggml_context * ctx) {
1696    size_t max_size = 0;
1697
1698    for (struct ggml_tensor * tensor = ggml_get_first_tensor(ctx); tensor != NULL; tensor = ggml_get_next_tensor(ctx, tensor)) {
1699        size_t bytes = ggml_nbytes(tensor);
1700        max_size = MAX(max_size, bytes);
1701    }
1702
1703    return max_size;
1704}
1705
1706////////////////////////////////////////////////////////////////////////////////
1707
1708static struct ggml_object * ggml_new_object(struct ggml_context * ctx, enum ggml_object_type type, size_t size) {
1709    // always insert objects at the end of the context's memory pool
1710    struct ggml_object * obj_cur = ctx->objects_end;
1711
1712    const size_t cur_offs = obj_cur == NULL ? 0 : obj_cur->offs;
1713    const size_t cur_size = obj_cur == NULL ? 0 : obj_cur->size;
1714    const size_t cur_end  = cur_offs + cur_size;
1715
1716    // align to GGML_MEM_ALIGN
1717    GGML_ASSERT(size <= SIZE_MAX - (GGML_MEM_ALIGN - 1));
1718    size_t size_needed = GGML_PAD(size, GGML_MEM_ALIGN);
1719
1720    char * const mem_buffer = ctx->mem_buffer;
1721    struct ggml_object * const obj_new = (struct ggml_object *)(mem_buffer + cur_end);
1722
1723    // integer overflow checks
1724    if (cur_end > SIZE_MAX - size_needed) {
1725        GGML_LOG_WARN("%s: overflow detected in cur_end (%zu) + size_needed (%zu)\n", __func__, cur_end, size_needed);
1726        return NULL;
1727    }
1728    if (cur_end + size_needed > SIZE_MAX - GGML_OBJECT_SIZE) {
1729        GGML_LOG_WARN("%s: overflow detected in cur_end (%zu) + size_needed (%zu) + GGML_OBJECT_SIZE (%zu)\n", __func__,
1730                cur_end, size_needed, (size_t) GGML_OBJECT_SIZE);
1731        return NULL;
1732    }
1733
1734    if (cur_end + size_needed + GGML_OBJECT_SIZE > ctx->mem_size) {
1735        GGML_LOG_WARN("%s: not enough space in the context's memory pool (needed %zu, available %zu)\n",
1736                __func__, cur_end + size_needed + GGML_OBJECT_SIZE, ctx->mem_size);
1737#ifndef NDEBUG
1738        GGML_ABORT("not enough space in the context's memory pool");
1739#endif
1740        return NULL;
1741    }
1742
1743    *obj_new = (struct ggml_object) {
1744        .offs = cur_end + GGML_OBJECT_SIZE,
1745        .size = size_needed,
1746        .next = NULL,
1747        .type = type,
1748    };
1749
1750    GGML_ASSERT_ALIGNED(mem_buffer + obj_new->offs);
1751
1752    if (obj_cur != NULL) {
1753        obj_cur->next = obj_new;
1754    } else {
1755        // this is the first object in this context
1756        ctx->objects_begin = obj_new;
1757    }
1758
1759    ctx->objects_end = obj_new;
1760
1761    //printf("%s: inserted new object at %zu, size = %zu\n", __func__, cur_end, obj_new->size);
1762
1763    return obj_new;
1764}
1765
1766static struct ggml_tensor * ggml_new_tensor_impl(
1767        struct ggml_context * ctx,
1768        enum   ggml_type      type,
1769        int                   n_dims,
1770        const int64_t       * ne,
1771        struct ggml_tensor  * view_src,
1772        size_t                view_offs) {
1773
1774    GGML_ASSERT(type >= 0 && type < GGML_TYPE_COUNT);
1775    GGML_ASSERT(n_dims >= 1 && n_dims <= GGML_MAX_DIMS);
1776
1777    // find the base tensor and absolute offset
1778    if (view_src != NULL && view_src->view_src != NULL) {
1779        view_offs += view_src->view_offs;
1780        view_src   = view_src->view_src;
1781    }
1782
1783    size_t data_size = ggml_row_size(type, ne[0]);
1784    for (int i = 1; i < n_dims; i++) {
1785        data_size *= ne[i];
1786    }
1787
1788    GGML_ASSERT(view_src == NULL || data_size == 0 || data_size + view_offs <= ggml_nbytes(view_src));
1789
1790    void * data = view_src != NULL ? view_src->data : NULL;
1791    if (data != NULL) {
1792        data = (char *) data + view_offs;
1793    }
1794
1795    size_t obj_alloc_size = 0;
1796
1797    if (view_src == NULL && !ctx->no_alloc) {
1798        // allocate tensor data in the context's memory pool
1799        obj_alloc_size = data_size;
1800    }
1801
1802    GGML_ASSERT(GGML_TENSOR_SIZE <= SIZE_MAX - obj_alloc_size);
1803
1804    struct ggml_object * const obj_new = ggml_new_object(ctx, GGML_OBJECT_TYPE_TENSOR, GGML_TENSOR_SIZE + obj_alloc_size);
1805    GGML_ASSERT(obj_new);
1806
1807    struct ggml_tensor * const result = (struct ggml_tensor *)((char *)ctx->mem_buffer + obj_new->offs);
1808
1809    *result = (struct ggml_tensor) {
1810        /*.type         =*/ type,
1811        /*.buffer       =*/ NULL,
1812        /*.ne           =*/ { 1, 1, 1, 1 },
1813        /*.nb           =*/ { 0, 0, 0, 0 },
1814        /*.op           =*/ GGML_OP_NONE,
1815        /*.op_params    =*/ { 0 },
1816        /*.flags        =*/ 0,
1817        /*.src          =*/ { NULL },
1818        /*.view_src     =*/ view_src,
1819        /*.view_offs    =*/ view_offs,
1820        /*.data         =*/ obj_alloc_size > 0 ? (void *)(result + 1) : data,
1821        /*.name         =*/ { 0 },
1822        /*.extra        =*/ NULL,
1823        /*.padding      =*/ { 0 },
1824    };
1825
1826    // TODO: this should not be needed as long as we don't rely on aligned SIMD loads
1827    //GGML_ASSERT_ALIGNED(result->data);
1828
1829    for (int i = 0; i < n_dims; i++) {
1830        result->ne[i] = ne[i];
1831    }
1832
1833    result->nb[0] = ggml_type_size(type);
1834    result->nb[1] = result->nb[0]*(result->ne[0]/ggml_blck_size(type));
1835    for (int i = 2; i < GGML_MAX_DIMS; i++) {
1836        result->nb[i] = result->nb[i - 1]*result->ne[i - 1];
1837    }
1838
1839    ctx->n_objects++;
1840
1841    return result;
1842}
1843
1844struct ggml_tensor * ggml_new_tensor(
1845        struct ggml_context * ctx,
1846        enum   ggml_type      type,
1847        int                   n_dims,
1848        const int64_t       * ne) {
1849    return ggml_new_tensor_impl(ctx, type, n_dims, ne, NULL, 0);
1850}
1851
1852struct ggml_tensor * ggml_new_tensor_1d(
1853        struct ggml_context * ctx,
1854        enum   ggml_type      type,
1855        int64_t ne0) {
1856    return ggml_new_tensor(ctx, type, 1, &ne0);
1857}
1858
1859struct ggml_tensor * ggml_new_tensor_2d(
1860        struct ggml_context * ctx,
1861        enum   ggml_type      type,
1862        int64_t ne0,
1863        int64_t ne1) {
1864    const int64_t ne[2] = { ne0, ne1 };
1865    return ggml_new_tensor(ctx, type, 2, ne);
1866}
1867
1868struct ggml_tensor * ggml_new_tensor_3d(
1869        struct ggml_context * ctx,
1870        enum   ggml_type      type,
1871        int64_t ne0,
1872        int64_t ne1,
1873        int64_t ne2) {
1874    const int64_t ne[3] = { ne0, ne1, ne2 };
1875    return ggml_new_tensor(ctx, type, 3, ne);
1876}
1877
1878struct ggml_tensor * ggml_new_tensor_4d(
1879        struct ggml_context * ctx,
1880        enum   ggml_type type,
1881        int64_t ne0,
1882        int64_t ne1,
1883        int64_t ne2,
1884        int64_t ne3) {
1885    const int64_t ne[4] = { ne0, ne1, ne2, ne3 };
1886    return ggml_new_tensor(ctx, type, 4, ne);
1887}
1888
1889void * ggml_new_buffer(struct ggml_context * ctx, size_t nbytes) {
1890    struct ggml_object * obj = ggml_new_object(ctx, GGML_OBJECT_TYPE_WORK_BUFFER, nbytes);
1891
1892    return (uint8_t *)ctx->mem_buffer + obj->offs;
1893}
1894
1895struct ggml_tensor * ggml_dup_tensor(struct ggml_context * ctx, const struct ggml_tensor * src) {
1896    return ggml_new_tensor(ctx, src->type, GGML_MAX_DIMS, src->ne);
1897}
1898
1899void ggml_unravel_index(const struct ggml_tensor * tensor, int64_t i, int64_t * i0, int64_t * i1, int64_t * i2, int64_t * i3) {
1900    const int64_t ne2 = tensor->ne[2];
1901    const int64_t ne1 = tensor->ne[1];
1902    const int64_t ne0 = tensor->ne[0];
1903
1904    const int64_t i3_ = (i/(ne2*ne1*ne0));
1905    const int64_t i2_ = (i - i3_*ne2*ne1*ne0)/(ne1*ne0);
1906    const int64_t i1_ = (i - i3_*ne2*ne1*ne0 - i2_*ne1*ne0)/ne0;
1907    const int64_t i0_ = (i - i3_*ne2*ne1*ne0 - i2_*ne1*ne0 - i1_*ne0);
1908
1909    if (i0) {
1910        * i0 = i0_;
1911    }
1912    if (i1) {
1913        * i1 = i1_;
1914    }
1915    if (i2) {
1916        * i2 = i2_;
1917    }
1918    if (i3) {
1919        * i3 = i3_;
1920    }
1921}
1922
1923void * ggml_get_data(const struct ggml_tensor * tensor) {
1924    return tensor->data;
1925}
1926
1927float * ggml_get_data_f32(const struct ggml_tensor * tensor) {
1928    assert(tensor->type == GGML_TYPE_F32);
1929    return (float *)(tensor->data);
1930}
1931
1932enum ggml_unary_op ggml_get_unary_op(const struct ggml_tensor * tensor) {
1933    GGML_ASSERT(tensor->op == GGML_OP_UNARY);
1934    return (enum ggml_unary_op) ggml_get_op_params_i32(tensor, 0);
1935}
1936
1937enum ggml_glu_op ggml_get_glu_op(const struct ggml_tensor * tensor) {
1938    GGML_ASSERT(tensor->op == GGML_OP_GLU);
1939    return (enum ggml_glu_op) ggml_get_op_params_i32(tensor, 0);
1940}
1941
1942const char * ggml_get_name(const struct ggml_tensor * tensor) {
1943    return tensor->name;
1944}
1945
1946struct ggml_tensor * ggml_set_name(struct ggml_tensor * tensor, const char * name) {
1947    size_t i;
1948    for (i = 0; i < sizeof(tensor->name) - 1 && name[i] != '\0'; i++) {
1949        tensor->name[i] = name[i];
1950    }
1951    tensor->name[i] = '\0';
1952    return tensor;
1953}
1954
1955struct ggml_tensor * ggml_format_name(struct ggml_tensor * tensor, const char * fmt, ...) {
1956    va_list args;
1957    va_start(args, fmt);
1958    vsnprintf(tensor->name, sizeof(tensor->name), fmt, args);
1959    va_end(args);
1960    return tensor;
1961}
1962
1963struct ggml_tensor * ggml_view_tensor(
1964        struct ggml_context * ctx,
1965        struct ggml_tensor  * src) {
1966    struct ggml_tensor * result = ggml_new_tensor_impl(ctx, src->type, GGML_MAX_DIMS, src->ne, src, 0);
1967    ggml_format_name(result, "%s (view)", src->name);
1968
1969    for (int i = 0; i < GGML_MAX_DIMS; i++) {
1970        result->nb[i] = src->nb[i];
1971    }
1972
1973    return result;
1974}
1975
1976struct ggml_tensor * ggml_get_first_tensor(const struct ggml_context * ctx) {
1977    struct ggml_object * obj = ctx->objects_begin;
1978
1979    char * const mem_buffer = ctx->mem_buffer;
1980
1981    while (obj != NULL) {
1982        if (obj->type == GGML_OBJECT_TYPE_TENSOR) {
1983            return (struct ggml_tensor *)(mem_buffer + obj->offs);
1984        }
1985
1986        obj = obj->next;
1987    }
1988
1989    return NULL;
1990}
1991
1992struct ggml_tensor * ggml_get_next_tensor(const struct ggml_context * ctx, struct ggml_tensor * tensor) {
1993    struct ggml_object * obj = (struct ggml_object *) ((char *)tensor - GGML_OBJECT_SIZE);
1994    obj = obj->next;
1995
1996    char * const mem_buffer = ctx->mem_buffer;
1997
1998    while (obj != NULL) {
1999        if (obj->type == GGML_OBJECT_TYPE_TENSOR) {
2000            return (struct ggml_tensor *)(mem_buffer + obj->offs);
2001        }
2002
2003        obj = obj->next;
2004    }
2005
2006    return NULL;
2007}
2008
2009struct ggml_tensor * ggml_get_tensor(struct ggml_context * ctx, const char * name) {
2010    struct ggml_object * obj = ctx->objects_begin;
2011
2012    char * const mem_buffer = ctx->mem_buffer;
2013
2014    while (obj != NULL) {
2015        if (obj->type == GGML_OBJECT_TYPE_TENSOR) {
2016            struct ggml_tensor * cur = (struct ggml_tensor *)(mem_buffer + obj->offs);
2017            if (strcmp(cur->name, name) == 0) {
2018                return cur;
2019            }
2020        }
2021
2022        obj = obj->next;
2023    }
2024
2025    return NULL;
2026}
2027
2028////////////////////////////////////////////////////////////////////////////////
2029
2030// ggml_dup
2031
2032static struct ggml_tensor * ggml_dup_impl(
2033        struct ggml_context * ctx,
2034        struct ggml_tensor  * a,
2035        bool                  inplace) {
2036    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
2037
2038    result->op     = GGML_OP_DUP;
2039    result->src[0] = a;
2040
2041    return result;
2042}
2043
2044struct ggml_tensor * ggml_dup(
2045        struct ggml_context * ctx,
2046        struct ggml_tensor  * a) {
2047    return ggml_dup_impl(ctx, a, false);
2048}
2049
2050struct ggml_tensor * ggml_dup_inplace(
2051        struct ggml_context * ctx,
2052        struct ggml_tensor  * a) {
2053    return ggml_dup_impl(ctx, a, true);
2054}
2055
2056// ggml_add
2057
2058static struct ggml_tensor * ggml_add_impl(
2059        struct ggml_context * ctx,
2060        struct ggml_tensor  * a,
2061        struct ggml_tensor  * b,
2062        bool                  inplace) {
2063    GGML_ASSERT(ggml_can_repeat(b, a));
2064
2065    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
2066
2067    result->op     = GGML_OP_ADD;
2068    result->src[0] = a;
2069    result->src[1] = b;
2070
2071    return result;
2072}
2073
2074struct ggml_tensor * ggml_add(
2075        struct ggml_context * ctx,
2076        struct ggml_tensor  * a,
2077        struct ggml_tensor  * b) {
2078    return ggml_add_impl(ctx, a, b, false);
2079}
2080
2081struct ggml_tensor * ggml_add_inplace(
2082        struct ggml_context * ctx,
2083        struct ggml_tensor  * a,
2084        struct ggml_tensor  * b) {
2085    return ggml_add_impl(ctx, a, b, true);
2086}
2087
2088// ggml_add_cast
2089
2090static struct ggml_tensor * ggml_add_cast_impl(
2091        struct ggml_context * ctx,
2092        struct ggml_tensor  * a,
2093        struct ggml_tensor  * b,
2094        enum   ggml_type      type) {
2095    // TODO: support less-strict constraint
2096    //       GGML_ASSERT(ggml_can_repeat(b, a));
2097    GGML_ASSERT(ggml_can_repeat_rows(b, a));
2098
2099    // currently only supported for quantized input and f16
2100    GGML_ASSERT(ggml_is_quantized(a->type) ||
2101                a->type == GGML_TYPE_F16 ||
2102                a->type == GGML_TYPE_BF16);
2103
2104    struct ggml_tensor * result = ggml_new_tensor(ctx, type, GGML_MAX_DIMS, a->ne);
2105
2106    result->op     = GGML_OP_ADD;
2107    result->src[0] = a;
2108    result->src[1] = b;
2109
2110    return result;
2111}
2112
2113struct ggml_tensor * ggml_add_cast(
2114        struct ggml_context * ctx,
2115        struct ggml_tensor  * a,
2116        struct ggml_tensor  * b,
2117        enum   ggml_type      type) {
2118    return ggml_add_cast_impl(ctx, a, b, type);
2119}
2120
2121struct ggml_tensor * ggml_add_id(
2122            struct ggml_context * ctx,
2123            struct ggml_tensor  * a,
2124            struct ggml_tensor  * b,
2125            struct ggml_tensor  * ids) {
2126
2127    GGML_ASSERT(a->ne[0] == b->ne[0]);
2128    GGML_ASSERT(a->ne[1] == ids->ne[0]);
2129    GGML_ASSERT(a->ne[2] == ids->ne[1]);
2130    GGML_ASSERT(ids->type == GGML_TYPE_I32);
2131
2132    struct ggml_tensor * result = ggml_dup_tensor(ctx, a);
2133
2134    result->op     = GGML_OP_ADD_ID;
2135    result->src[0] = a;
2136    result->src[1] = b;
2137    result->src[2] = ids;
2138
2139    return result;
2140}
2141
2142// ggml_add1
2143
2144static struct ggml_tensor * ggml_add1_impl(
2145        struct ggml_context * ctx,
2146        struct ggml_tensor  * a,
2147        struct ggml_tensor  * b,
2148        bool                  inplace) {
2149    GGML_ASSERT(ggml_is_scalar(b));
2150    GGML_ASSERT(ggml_is_padded_1d(a));
2151
2152    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
2153
2154    result->op     = GGML_OP_ADD1;
2155    result->src[0] = a;
2156    result->src[1] = b;
2157
2158    return result;
2159}
2160
2161struct ggml_tensor * ggml_add1(
2162        struct ggml_context * ctx,
2163        struct ggml_tensor  * a,
2164        struct ggml_tensor  * b) {
2165    return ggml_add1_impl(ctx, a, b, false);
2166}
2167
2168struct ggml_tensor * ggml_add1_inplace(
2169        struct ggml_context * ctx,
2170        struct ggml_tensor  * a,
2171        struct ggml_tensor  * b) {
2172    return ggml_add1_impl(ctx, a, b, true);
2173}
2174
2175// ggml_acc
2176
2177static struct ggml_tensor * ggml_acc_impl(
2178        struct ggml_context * ctx,
2179        struct ggml_tensor  * a,
2180        struct ggml_tensor  * b,
2181        size_t                nb1,
2182        size_t                nb2,
2183        size_t                nb3,
2184        size_t                offset,
2185        bool                  inplace) {
2186    GGML_ASSERT(ggml_nelements(b) <= ggml_nelements(a));
2187    GGML_ASSERT(ggml_is_contiguous(a));
2188    GGML_ASSERT(a->type == GGML_TYPE_F32);
2189    GGML_ASSERT(b->type == GGML_TYPE_F32);
2190
2191    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
2192
2193    int32_t params[] = { nb1, nb2, nb3, offset, inplace ? 1 : 0 };
2194    ggml_set_op_params(result, params, sizeof(params));
2195
2196    result->op     = GGML_OP_ACC;
2197    result->src[0] = a;
2198    result->src[1] = b;
2199
2200    return result;
2201}
2202
2203struct ggml_tensor * ggml_acc(
2204        struct ggml_context * ctx,
2205        struct ggml_tensor  * a,
2206        struct ggml_tensor  * b,
2207        size_t                nb1,
2208        size_t                nb2,
2209        size_t                nb3,
2210        size_t                offset) {
2211    return ggml_acc_impl(ctx, a, b, nb1, nb2, nb3, offset, false);
2212}
2213
2214struct ggml_tensor * ggml_acc_inplace(
2215        struct ggml_context * ctx,
2216        struct ggml_tensor  * a,
2217        struct ggml_tensor  * b,
2218        size_t                nb1,
2219        size_t                nb2,
2220        size_t                nb3,
2221        size_t                offset) {
2222    return ggml_acc_impl(ctx, a, b, nb1, nb2, nb3, offset, true);
2223}
2224
2225// ggml_sub
2226
2227static struct ggml_tensor * ggml_sub_impl(
2228        struct ggml_context * ctx,
2229        struct ggml_tensor  * a,
2230        struct ggml_tensor  * b,
2231        bool                  inplace) {
2232    GGML_ASSERT(ggml_can_repeat(b, a));
2233
2234    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
2235
2236    result->op     = GGML_OP_SUB;
2237    result->src[0] = a;
2238    result->src[1] = b;
2239
2240    return result;
2241}
2242
2243struct ggml_tensor * ggml_sub(
2244        struct ggml_context * ctx,
2245        struct ggml_tensor  * a,
2246        struct ggml_tensor  * b) {
2247    return ggml_sub_impl(ctx, a, b, false);
2248}
2249
2250struct ggml_tensor * ggml_sub_inplace(
2251        struct ggml_context * ctx,
2252        struct ggml_tensor  * a,
2253        struct ggml_tensor  * b) {
2254    return ggml_sub_impl(ctx, a, b, true);
2255}
2256
2257// ggml_mul
2258
2259static struct ggml_tensor * ggml_mul_impl(
2260        struct ggml_context * ctx,
2261        struct ggml_tensor  * a,
2262        struct ggml_tensor  * b,
2263        bool                  inplace) {
2264    GGML_ASSERT(ggml_can_repeat(b, a));
2265
2266    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
2267
2268    result->op     = GGML_OP_MUL;
2269    result->src[0] = a;
2270    result->src[1] = b;
2271
2272    return result;
2273}
2274
2275struct ggml_tensor * ggml_mul(
2276        struct ggml_context * ctx,
2277        struct ggml_tensor  * a,
2278        struct ggml_tensor  * b) {
2279    return ggml_mul_impl(ctx, a, b, false);
2280}
2281
2282struct ggml_tensor * ggml_mul_inplace(
2283        struct ggml_context * ctx,
2284        struct ggml_tensor  * a,
2285        struct ggml_tensor  * b) {
2286    return ggml_mul_impl(ctx, a, b, true);
2287}
2288
2289// ggml_div
2290
2291static struct ggml_tensor * ggml_div_impl(
2292        struct ggml_context * ctx,
2293        struct ggml_tensor  * a,
2294        struct ggml_tensor  * b,
2295        bool                  inplace) {
2296    GGML_ASSERT(ggml_can_repeat(b, a));
2297
2298    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
2299
2300    result->op     = GGML_OP_DIV;
2301    result->src[0] = a;
2302    result->src[1] = b;
2303
2304    return result;
2305}
2306
2307struct ggml_tensor * ggml_div(
2308        struct ggml_context * ctx,
2309        struct ggml_tensor  * a,
2310        struct ggml_tensor  * b) {
2311    return ggml_div_impl(ctx, a, b, false);
2312}
2313
2314struct ggml_tensor * ggml_div_inplace(
2315        struct ggml_context * ctx,
2316        struct ggml_tensor  * a,
2317        struct ggml_tensor  * b) {
2318    return ggml_div_impl(ctx, a, b, true);
2319}
2320
2321// ggml_sqr
2322
2323static struct ggml_tensor * ggml_sqr_impl(
2324        struct ggml_context * ctx,
2325        struct ggml_tensor  * a,
2326        bool                  inplace) {
2327    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
2328
2329    result->op     = GGML_OP_SQR;
2330    result->src[0] = a;
2331
2332    return result;
2333}
2334
2335struct ggml_tensor * ggml_sqr(
2336        struct ggml_context * ctx,
2337        struct ggml_tensor  * a) {
2338    return ggml_sqr_impl(ctx, a, false);
2339}
2340
2341struct ggml_tensor * ggml_sqr_inplace(
2342        struct ggml_context * ctx,
2343        struct ggml_tensor  * a) {
2344    return ggml_sqr_impl(ctx, a, true);
2345}
2346
2347// ggml_sqrt
2348
2349static struct ggml_tensor * ggml_sqrt_impl(
2350        struct ggml_context * ctx,
2351        struct ggml_tensor  * a,
2352        bool                  inplace) {
2353    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
2354
2355    result->op     = GGML_OP_SQRT;
2356    result->src[0] = a;
2357
2358    return result;
2359}
2360
2361struct ggml_tensor * ggml_sqrt(
2362        struct ggml_context * ctx,
2363        struct ggml_tensor  * a) {
2364    return ggml_sqrt_impl(ctx, a, false);
2365}
2366
2367struct ggml_tensor * ggml_sqrt_inplace(
2368        struct ggml_context * ctx,
2369        struct ggml_tensor  * a) {
2370    return ggml_sqrt_impl(ctx, a, true);
2371}
2372
2373// ggml_log
2374
2375static struct ggml_tensor * ggml_log_impl(
2376        struct ggml_context * ctx,
2377        struct ggml_tensor  * a,
2378        bool                  inplace) {
2379    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
2380
2381    result->op     = GGML_OP_LOG;
2382    result->src[0] = a;
2383
2384    return result;
2385}
2386
2387struct ggml_tensor * ggml_log(
2388        struct ggml_context * ctx,
2389        struct ggml_tensor  * a) {
2390    return ggml_log_impl(ctx, a, false);
2391}
2392
2393struct ggml_tensor * ggml_log_inplace(
2394        struct ggml_context * ctx,
2395        struct ggml_tensor  * a) {
2396    return ggml_log_impl(ctx, a, true);
2397}
2398
2399struct ggml_tensor * ggml_expm1(
2400        struct ggml_context * ctx,
2401        struct ggml_tensor  * a) {
2402    return ggml_unary(ctx, a, GGML_UNARY_OP_EXPM1);
2403}
2404
2405struct ggml_tensor * ggml_expm1_inplace(
2406        struct ggml_context * ctx,
2407        struct ggml_tensor  * a) {
2408    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_EXPM1);
2409}
2410
2411struct ggml_tensor * ggml_softplus(
2412        struct ggml_context * ctx,
2413        struct ggml_tensor  * a) {
2414    return ggml_unary(ctx, a, GGML_UNARY_OP_SOFTPLUS);
2415}
2416
2417struct ggml_tensor * ggml_softplus_inplace(
2418        struct ggml_context * ctx,
2419        struct ggml_tensor  * a) {
2420    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_SOFTPLUS);
2421}
2422
2423// ggml_sin
2424
2425static struct ggml_tensor * ggml_sin_impl(
2426        struct ggml_context * ctx,
2427        struct ggml_tensor  * a,
2428        bool                  inplace) {
2429    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
2430
2431    result->op     = GGML_OP_SIN;
2432    result->src[0] = a;
2433
2434    return result;
2435}
2436
2437struct ggml_tensor * ggml_sin(
2438        struct ggml_context * ctx,
2439        struct ggml_tensor  * a) {
2440    return ggml_sin_impl(ctx, a, false);
2441}
2442
2443struct ggml_tensor * ggml_sin_inplace(
2444        struct ggml_context * ctx,
2445        struct ggml_tensor  * a) {
2446    return ggml_sin_impl(ctx, a, true);
2447}
2448
2449// ggml_cos
2450
2451static struct ggml_tensor * ggml_cos_impl(
2452        struct ggml_context * ctx,
2453        struct ggml_tensor  * a,
2454        bool                  inplace) {
2455    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
2456
2457    result->op     = GGML_OP_COS;
2458    result->src[0] = a;
2459
2460    return result;
2461}
2462
2463struct ggml_tensor * ggml_cos(
2464        struct ggml_context * ctx,
2465        struct ggml_tensor  * a) {
2466    return ggml_cos_impl(ctx, a, false);
2467}
2468
2469struct ggml_tensor * ggml_cos_inplace(
2470        struct ggml_context * ctx,
2471        struct ggml_tensor  * a) {
2472    return ggml_cos_impl(ctx, a, true);
2473}
2474
2475// ggml_sum
2476
2477struct ggml_tensor * ggml_sum(
2478        struct ggml_context * ctx,
2479        struct ggml_tensor  * a) {
2480    struct ggml_tensor * result = ggml_new_tensor_1d(ctx, a->type, 1);
2481
2482    result->op     = GGML_OP_SUM;
2483    result->src[0] = a;
2484
2485    return result;
2486}
2487
2488// ggml_sum_rows
2489
2490struct ggml_tensor * ggml_sum_rows(
2491        struct ggml_context * ctx,
2492        struct ggml_tensor  * a) {
2493    int64_t ne[GGML_MAX_DIMS] = { 1 };
2494    for (int i = 1; i < GGML_MAX_DIMS; ++i) {
2495        ne[i] = a->ne[i];
2496    }
2497
2498    struct ggml_tensor * result = ggml_new_tensor(ctx, a->type, GGML_MAX_DIMS, ne);
2499
2500    result->op     = GGML_OP_SUM_ROWS;
2501    result->src[0] = a;
2502
2503    return result;
2504}
2505
2506// ggml_cumsum
2507
2508struct ggml_tensor * ggml_cumsum(
2509        struct ggml_context * ctx,
2510        struct ggml_tensor  * a) {
2511    GGML_ASSERT(a->type == GGML_TYPE_F32);
2512
2513    struct ggml_tensor * result = ggml_dup_tensor(ctx, a);
2514
2515    result->op     = GGML_OP_CUMSUM;
2516    result->src[0] = a;
2517
2518    return result;
2519}
2520
2521// ggml_mean
2522
2523struct ggml_tensor * ggml_mean(
2524        struct ggml_context * ctx,
2525        struct ggml_tensor  * a) {
2526    int64_t ne[4] = { 1, a->ne[1], a->ne[2], a->ne[3] };
2527    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
2528
2529    result->op     = GGML_OP_MEAN;
2530    result->src[0] = a;
2531
2532    return result;
2533}
2534
2535// ggml_argmax
2536
2537struct ggml_tensor * ggml_argmax(
2538        struct ggml_context * ctx,
2539        struct ggml_tensor  * a) {
2540    GGML_ASSERT(ggml_is_matrix(a));
2541    GGML_ASSERT(a->ne[0] <= INT32_MAX);
2542
2543    struct ggml_tensor * result = ggml_new_tensor_1d(ctx, GGML_TYPE_I32, a->ne[1]);
2544
2545    result->op     = GGML_OP_ARGMAX;
2546    result->src[0] = a;
2547
2548    return result;
2549}
2550
2551// ggml_count_equal
2552
2553struct ggml_tensor * ggml_count_equal(
2554        struct ggml_context * ctx,
2555        struct ggml_tensor  * a,
2556        struct ggml_tensor  * b) {
2557    GGML_ASSERT(ggml_are_same_shape(a, b));
2558
2559    struct ggml_tensor * result = ggml_new_tensor_1d(ctx, GGML_TYPE_I64, 1);
2560
2561    result->op     = GGML_OP_COUNT_EQUAL;
2562    result->src[0] = a;
2563    result->src[1] = b;
2564
2565    return result;
2566}
2567
2568// ggml_repeat
2569
2570struct ggml_tensor * ggml_repeat(
2571        struct ggml_context * ctx,
2572        struct ggml_tensor  * a,
2573        struct ggml_tensor  * b) {
2574    GGML_ASSERT(ggml_can_repeat(a, b));
2575
2576    struct ggml_tensor * result = ggml_new_tensor(ctx, a->type, GGML_MAX_DIMS, b->ne);
2577
2578    result->op     = GGML_OP_REPEAT;
2579    result->src[0] = a;
2580
2581    return result;
2582}
2583
2584struct ggml_tensor * ggml_repeat_4d(
2585        struct ggml_context * ctx,
2586        struct ggml_tensor * a,
2587        int64_t ne0, int64_t ne1, int64_t ne2, int64_t ne3) {
2588    const bool can_repeat = ggml_is_empty(a) || (
2589        (ne0 % a->ne[0] == 0) &&
2590        (ne1 % a->ne[1] == 0) &&
2591        (ne2 % a->ne[2] == 0) &&
2592        (ne3 % a->ne[3] == 0)
2593    );
2594    GGML_ASSERT(can_repeat);
2595
2596    struct ggml_tensor * result = ggml_new_tensor_4d(ctx, a->type, ne0, ne1, ne2, ne3);
2597
2598    result->op     = GGML_OP_REPEAT;
2599    result->src[0] = a;
2600
2601    return result;
2602}
2603
2604// ggml_repeat_back
2605
2606struct ggml_tensor * ggml_repeat_back(
2607        struct ggml_context * ctx,
2608        struct ggml_tensor  * a,
2609        struct ggml_tensor  * b) {
2610    GGML_ASSERT(ggml_can_repeat(b, a));
2611
2612    struct ggml_tensor * result = ggml_new_tensor(ctx, a->type, GGML_MAX_DIMS, b->ne);
2613
2614    result->op     = GGML_OP_REPEAT_BACK;
2615    result->src[0] = a;
2616
2617    return result;
2618}
2619
2620// ggml_concat
2621
2622struct ggml_tensor * ggml_concat(
2623    struct ggml_context * ctx,
2624    struct ggml_tensor  * a,
2625    struct ggml_tensor  * b,
2626    int                   dim) {
2627    GGML_ASSERT(dim >= 0 && dim < GGML_MAX_DIMS);
2628    GGML_ASSERT(a->type == b->type);
2629
2630    int64_t ne[GGML_MAX_DIMS];
2631    for (int d = 0; d < GGML_MAX_DIMS; ++d) {
2632        if (d == dim) {
2633            ne[d] = a->ne[d] + b->ne[d];
2634            continue;
2635        }
2636        GGML_ASSERT(a->ne[d] == b->ne[d]);
2637        ne[d] = a->ne[d];
2638    }
2639
2640    struct ggml_tensor * result = ggml_new_tensor(ctx, a->type, GGML_MAX_DIMS, ne);
2641
2642    ggml_set_op_params_i32(result, 0, dim);
2643
2644    result->op     = GGML_OP_CONCAT;
2645    result->src[0] = a;
2646    result->src[1] = b;
2647
2648    return result;
2649}
2650
2651// ggml_abs
2652
2653struct ggml_tensor * ggml_abs(
2654        struct ggml_context * ctx,
2655        struct ggml_tensor  * a) {
2656    return ggml_unary(ctx, a, GGML_UNARY_OP_ABS);
2657}
2658
2659struct ggml_tensor * ggml_abs_inplace(
2660        struct ggml_context * ctx,
2661        struct ggml_tensor  * a) {
2662    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_ABS);
2663}
2664
2665// ggml_sgn
2666
2667struct ggml_tensor * ggml_sgn(
2668        struct ggml_context * ctx,
2669        struct ggml_tensor  * a) {
2670    return ggml_unary(ctx, a, GGML_UNARY_OP_SGN);
2671}
2672
2673struct ggml_tensor * ggml_sgn_inplace(
2674        struct ggml_context * ctx,
2675        struct ggml_tensor  * a) {
2676    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_SGN);
2677}
2678
2679// ggml_neg
2680
2681struct ggml_tensor * ggml_neg(
2682        struct ggml_context * ctx,
2683        struct ggml_tensor  * a) {
2684    return ggml_unary(ctx, a, GGML_UNARY_OP_NEG);
2685}
2686
2687struct ggml_tensor * ggml_neg_inplace(
2688        struct ggml_context * ctx,
2689        struct ggml_tensor  * a) {
2690    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_NEG);
2691}
2692
2693// ggml_step
2694
2695struct ggml_tensor * ggml_step(
2696        struct ggml_context * ctx,
2697        struct ggml_tensor  * a) {
2698    return ggml_unary(ctx, a, GGML_UNARY_OP_STEP);
2699}
2700
2701struct ggml_tensor * ggml_step_inplace(
2702        struct ggml_context * ctx,
2703        struct ggml_tensor  * a) {
2704    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_STEP);
2705}
2706
2707// ggml_tanh
2708
2709struct ggml_tensor * ggml_tanh(
2710        struct ggml_context * ctx,
2711        struct ggml_tensor  * a) {
2712    return ggml_unary(ctx, a, GGML_UNARY_OP_TANH);
2713}
2714
2715struct ggml_tensor * ggml_tanh_inplace(
2716        struct ggml_context * ctx,
2717        struct ggml_tensor  * a) {
2718    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_TANH);
2719}
2720
2721// ggml_elu
2722
2723struct ggml_tensor * ggml_elu(
2724    struct ggml_context * ctx,
2725    struct ggml_tensor  * a) {
2726    return ggml_unary(ctx, a, GGML_UNARY_OP_ELU);
2727}
2728
2729struct ggml_tensor * ggml_elu_inplace(
2730    struct ggml_context * ctx,
2731    struct ggml_tensor  * a) {
2732    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_ELU);
2733}
2734
2735// ggml_relu
2736
2737struct ggml_tensor * ggml_relu(
2738        struct ggml_context * ctx,
2739        struct ggml_tensor  * a) {
2740    return ggml_unary(ctx, a, GGML_UNARY_OP_RELU);
2741}
2742
2743struct ggml_tensor * ggml_relu_inplace(
2744        struct ggml_context * ctx,
2745        struct ggml_tensor  * a) {
2746    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_RELU);
2747}
2748
2749// ggml_leaky_relu
2750
2751struct ggml_tensor * ggml_leaky_relu(
2752        struct ggml_context * ctx,
2753        struct ggml_tensor  * a,
2754        float                 negative_slope,
2755        bool                  inplace) {
2756    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
2757
2758    ggml_set_op_params(result, &negative_slope, sizeof(negative_slope));
2759
2760    result->op     = GGML_OP_LEAKY_RELU;
2761    result->src[0] = a;
2762
2763    return result;
2764}
2765
2766// ggml_sigmoid
2767
2768struct ggml_tensor * ggml_sigmoid(
2769        struct ggml_context * ctx,
2770        struct ggml_tensor  * a) {
2771    return ggml_unary(ctx, a, GGML_UNARY_OP_SIGMOID);
2772}
2773
2774struct ggml_tensor * ggml_sigmoid_inplace(
2775        struct ggml_context * ctx,
2776        struct ggml_tensor  * a) {
2777    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_SIGMOID);
2778}
2779
2780// ggml_gelu
2781
2782struct ggml_tensor * ggml_gelu(
2783        struct ggml_context * ctx,
2784        struct ggml_tensor  * a) {
2785    return ggml_unary(ctx, a, GGML_UNARY_OP_GELU);
2786}
2787
2788struct ggml_tensor * ggml_gelu_inplace(
2789        struct ggml_context * ctx,
2790        struct ggml_tensor  * a) {
2791    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_GELU);
2792}
2793
2794// ggml_gelu_erf
2795
2796struct ggml_tensor * ggml_gelu_erf(
2797        struct ggml_context * ctx,
2798        struct ggml_tensor  * a) {
2799    return ggml_unary(ctx, a, GGML_UNARY_OP_GELU_ERF);
2800}
2801
2802struct ggml_tensor * ggml_gelu_erf_inplace(
2803        struct ggml_context * ctx,
2804        struct ggml_tensor  * a) {
2805    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_GELU_ERF);
2806}
2807
2808// ggml_gelu_quick
2809
2810struct ggml_tensor * ggml_gelu_quick(
2811        struct ggml_context * ctx,
2812        struct ggml_tensor  * a) {
2813    return ggml_unary(ctx, a, GGML_UNARY_OP_GELU_QUICK);
2814}
2815
2816struct ggml_tensor * ggml_gelu_quick_inplace(
2817        struct ggml_context * ctx,
2818        struct ggml_tensor  * a) {
2819    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_GELU_QUICK);
2820}
2821
2822// ggml_silu
2823
2824struct ggml_tensor * ggml_silu(
2825        struct ggml_context * ctx,
2826        struct ggml_tensor  * a) {
2827    return ggml_unary(ctx, a, GGML_UNARY_OP_SILU);
2828}
2829
2830struct ggml_tensor * ggml_silu_inplace(
2831        struct ggml_context * ctx,
2832        struct ggml_tensor  * a) {
2833    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_SILU);
2834}
2835
2836// ggml_xielu
2837
2838struct ggml_tensor * ggml_xielu(
2839        struct ggml_context * ctx,
2840        struct ggml_tensor  * a,
2841        float alpha_n,
2842        float alpha_p,
2843        float beta,
2844        float eps) {
2845    struct ggml_tensor * result = ggml_dup_tensor(ctx, a);
2846
2847    ggml_set_op_params_i32(result, 0, (int32_t) GGML_UNARY_OP_XIELU);
2848    ggml_set_op_params_f32(result, 1, beta + ggml_compute_softplus_f32(alpha_n));
2849    ggml_set_op_params_f32(result, 2, ggml_compute_softplus_f32(alpha_p));
2850    ggml_set_op_params_f32(result, 3, beta);
2851    ggml_set_op_params_f32(result, 4, eps);
2852
2853    result->op     = GGML_OP_UNARY;
2854    result->src[0] = a;
2855
2856    return result;
2857}
2858
2859// ggml_silu_back
2860
2861struct ggml_tensor * ggml_silu_back(
2862        struct ggml_context * ctx,
2863        struct ggml_tensor  * a,
2864        struct ggml_tensor  * b) {
2865    struct ggml_tensor * result = ggml_dup_tensor(ctx, a);
2866
2867    result->op     = GGML_OP_SILU_BACK;
2868    result->src[0] = a;
2869    result->src[1] = b;
2870
2871    return result;
2872}
2873
2874// ggml hardswish
2875
2876struct ggml_tensor * ggml_hardswish(
2877        struct ggml_context * ctx,
2878        struct ggml_tensor  * a) {
2879    return ggml_unary(ctx, a, GGML_UNARY_OP_HARDSWISH);
2880}
2881
2882// ggml hardsigmoid
2883
2884struct ggml_tensor * ggml_hardsigmoid(
2885        struct ggml_context * ctx,
2886        struct ggml_tensor  * a) {
2887    return ggml_unary(ctx, a, GGML_UNARY_OP_HARDSIGMOID);
2888}
2889
2890// ggml exp
2891
2892struct ggml_tensor * ggml_exp(
2893        struct ggml_context * ctx,
2894        struct ggml_tensor  * a) {
2895    return ggml_unary(ctx, a, GGML_UNARY_OP_EXP);
2896}
2897
2898struct ggml_tensor * ggml_exp_inplace(
2899        struct ggml_context * ctx,
2900        struct ggml_tensor  * a) {
2901    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_EXP);
2902}
2903
2904// ggml_glu
2905
2906static struct ggml_tensor * ggml_glu_impl(
2907        struct ggml_context * ctx,
2908        struct ggml_tensor  * a,
2909        struct ggml_tensor  * b,
2910        enum ggml_glu_op      op,
2911        bool                  swapped) {
2912    GGML_ASSERT(ggml_is_contiguous_1(a));
2913
2914    if (b) {
2915        GGML_ASSERT(ggml_is_contiguous_1(b));
2916        GGML_ASSERT(ggml_are_same_shape(a, b));
2917        GGML_ASSERT(a->type == b->type);
2918    }
2919
2920    int64_t ne[GGML_MAX_DIMS] = { a->ne[0] / 2 }; for (int i = 1; i < GGML_MAX_DIMS; i++) ne[i] = a->ne[i];
2921    struct ggml_tensor * result = ggml_new_tensor_impl(ctx, a->type, GGML_MAX_DIMS, b ? a->ne : ne, NULL, 0);
2922
2923    ggml_set_op_params_i32(result, 0, (int32_t) op);
2924    ggml_set_op_params_i32(result, 1, (int32_t) swapped);
2925
2926    result->op     = GGML_OP_GLU;
2927    result->src[0] = a;
2928    result->src[1] = b;
2929
2930    return result;
2931}
2932
2933// ggml_floor
2934
2935struct ggml_tensor * ggml_floor(
2936        struct ggml_context * ctx,
2937        struct ggml_tensor  * a) {
2938    return ggml_unary(ctx, a, GGML_UNARY_OP_FLOOR);
2939}
2940
2941struct ggml_tensor * ggml_floor_inplace(
2942        struct ggml_context * ctx,
2943        struct ggml_tensor  * a) {
2944    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_FLOOR);
2945}
2946
2947// ggml_ceil
2948
2949struct ggml_tensor * ggml_ceil(
2950        struct ggml_context * ctx,
2951        struct ggml_tensor  * a) {
2952    return ggml_unary(ctx, a, GGML_UNARY_OP_CEIL);
2953}
2954
2955struct ggml_tensor * ggml_ceil_inplace(
2956        struct ggml_context * ctx,
2957        struct ggml_tensor  * a) {
2958    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_CEIL);
2959}
2960
2961//ggml_round
2962
2963struct ggml_tensor * ggml_round(
2964        struct ggml_context * ctx,
2965        struct ggml_tensor  * a) {
2966    return ggml_unary(ctx, a, GGML_UNARY_OP_ROUND);
2967}
2968
2969struct ggml_tensor * ggml_round_inplace(
2970        struct ggml_context * ctx,
2971        struct ggml_tensor  * a) {
2972    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_ROUND);
2973}
2974
2975//ggml_trunc
2976
2977struct ggml_tensor * ggml_trunc(
2978        struct ggml_context * ctx,
2979        struct ggml_tensor  * a) {
2980    return ggml_unary(ctx, a, GGML_UNARY_OP_TRUNC);
2981}
2982
2983struct ggml_tensor * ggml_trunc_inplace(
2984        struct ggml_context * ctx,
2985        struct ggml_tensor  * a) {
2986    return ggml_unary_inplace(ctx, a, GGML_UNARY_OP_TRUNC);
2987}
2988
2989struct ggml_tensor * ggml_glu(
2990        struct ggml_context * ctx,
2991        struct ggml_tensor  * a,
2992        enum ggml_glu_op      op,
2993        bool                  swapped) {
2994    return ggml_glu_impl(ctx, a, NULL, op, swapped);
2995}
2996
2997struct ggml_tensor * ggml_glu_split(
2998        struct ggml_context * ctx,
2999        struct ggml_tensor  * a,
3000        struct ggml_tensor  * b,
3001        enum ggml_glu_op      op) {
3002    return ggml_glu_impl(ctx, a, b, op, false);
3003}
3004
3005// ggml_reglu
3006
3007struct ggml_tensor * ggml_reglu(
3008        struct ggml_context * ctx,
3009        struct ggml_tensor  * a) {
3010    return ggml_glu_impl(ctx, a, NULL, GGML_GLU_OP_REGLU, false);
3011}
3012
3013struct ggml_tensor * ggml_reglu_swapped(
3014        struct ggml_context * ctx,
3015        struct ggml_tensor  * a) {
3016    return ggml_glu_impl(ctx, a, NULL, GGML_GLU_OP_REGLU, true);
3017}
3018
3019struct ggml_tensor * ggml_reglu_split(
3020        struct ggml_context * ctx,
3021        struct ggml_tensor  * a,
3022        struct ggml_tensor  * b) {
3023    return ggml_glu_impl(ctx, a, b, GGML_GLU_OP_REGLU, false);
3024}
3025
3026// ggml_geglu
3027
3028struct ggml_tensor * ggml_geglu(
3029        struct ggml_context * ctx,
3030        struct ggml_tensor  * a) {
3031    return ggml_glu_impl(ctx, a, NULL, GGML_GLU_OP_GEGLU, false);
3032}
3033
3034struct ggml_tensor * ggml_geglu_swapped(
3035        struct ggml_context * ctx,
3036        struct ggml_tensor  * a) {
3037    return ggml_glu_impl(ctx, a, NULL, GGML_GLU_OP_GEGLU, true);
3038}
3039
3040struct ggml_tensor * ggml_geglu_split(
3041        struct ggml_context * ctx,
3042        struct ggml_tensor  * a,
3043        struct ggml_tensor  * b) {
3044    return ggml_glu_impl(ctx, a, b, GGML_GLU_OP_GEGLU, false);
3045}
3046
3047// ggml_swiglu
3048
3049struct ggml_tensor * ggml_swiglu(
3050        struct ggml_context * ctx,
3051        struct ggml_tensor  * a) {
3052    return ggml_glu_impl(ctx, a, NULL, GGML_GLU_OP_SWIGLU, false);
3053}
3054
3055struct ggml_tensor * ggml_swiglu_swapped(
3056        struct ggml_context * ctx,
3057        struct ggml_tensor  * a) {
3058    return ggml_glu_impl(ctx, a, NULL, GGML_GLU_OP_SWIGLU, true);
3059}
3060
3061struct ggml_tensor * ggml_swiglu_split(
3062        struct ggml_context * ctx,
3063        struct ggml_tensor  * a,
3064        struct ggml_tensor  * b) {
3065    return ggml_glu_impl(ctx, a, b, GGML_GLU_OP_SWIGLU, false);
3066}
3067
3068// ggml_geglu_erf
3069
3070struct ggml_tensor * ggml_geglu_erf(
3071        struct ggml_context * ctx,
3072        struct ggml_tensor  * a) {
3073    return ggml_glu_impl(ctx, a, NULL, GGML_GLU_OP_GEGLU_ERF, false);
3074}
3075
3076struct ggml_tensor * ggml_geglu_erf_swapped(
3077        struct ggml_context * ctx,
3078        struct ggml_tensor  * a) {
3079    return ggml_glu_impl(ctx, a, NULL, GGML_GLU_OP_GEGLU_ERF, true);
3080}
3081
3082struct ggml_tensor * ggml_geglu_erf_split(
3083        struct ggml_context * ctx,
3084        struct ggml_tensor  * a,
3085        struct ggml_tensor  * b) {
3086    return ggml_glu_impl(ctx, a, b, GGML_GLU_OP_GEGLU_ERF, false);
3087}
3088
3089// ggml_geglu_quick
3090
3091struct ggml_tensor * ggml_geglu_quick(
3092        struct ggml_context * ctx,
3093        struct ggml_tensor  * a) {
3094    return ggml_glu_impl(ctx, a, NULL, GGML_GLU_OP_GEGLU_QUICK, false);
3095}
3096
3097struct ggml_tensor * ggml_geglu_quick_swapped(
3098        struct ggml_context * ctx,
3099        struct ggml_tensor  * a) {
3100    return ggml_glu_impl(ctx, a, NULL, GGML_GLU_OP_GEGLU_QUICK, true);
3101}
3102
3103struct ggml_tensor * ggml_geglu_quick_split(
3104        struct ggml_context * ctx,
3105        struct ggml_tensor  * a,
3106        struct ggml_tensor  * b) {
3107    return ggml_glu_impl(ctx, a, b, GGML_GLU_OP_GEGLU_QUICK, false);
3108}
3109
3110struct ggml_tensor * ggml_swiglu_oai(
3111        struct ggml_context * ctx,
3112        struct ggml_tensor  * a,
3113        struct ggml_tensor  * b,
3114        float                 alpha,
3115        float                 limit) {
3116    struct ggml_tensor * result = ggml_glu_impl(ctx, a, b, GGML_GLU_OP_SWIGLU_OAI, false);
3117    ggml_set_op_params_f32(result, 2, alpha);
3118    ggml_set_op_params_f32(result, 3, limit);
3119
3120    return result;
3121}
3122
3123struct ggml_tensor * ggml_swiglu_clamp(
3124        struct ggml_context * ctx,
3125        struct ggml_tensor  * a,
3126        struct ggml_tensor  * b,
3127        float                 limit) {
3128    struct ggml_tensor * result = ggml_glu_impl(ctx, a, b, GGML_GLU_OP_SWIGLU_CLAMP, false);
3129    ggml_set_op_params_f32(result, 3, limit);
3130
3131    return result;
3132}
3133
3134// ggml_norm
3135
3136static struct ggml_tensor * ggml_norm_impl(
3137        struct ggml_context * ctx,
3138        struct ggml_tensor  * a,
3139        float                 eps,
3140        bool                  inplace) {
3141    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
3142
3143    ggml_set_op_params(result, &eps, sizeof(eps));
3144
3145    result->op     = GGML_OP_NORM;
3146    result->src[0] = a;
3147
3148    return result;
3149}
3150
3151struct ggml_tensor * ggml_norm(
3152        struct ggml_context * ctx,
3153        struct ggml_tensor  * a,
3154        float                 eps) {
3155    return ggml_norm_impl(ctx, a, eps, false);
3156}
3157
3158struct ggml_tensor * ggml_norm_inplace(
3159        struct ggml_context * ctx,
3160        struct ggml_tensor  * a,
3161        float                 eps) {
3162    return ggml_norm_impl(ctx, a, eps, true);
3163}
3164
3165// ggml_rms_norm
3166
3167static struct ggml_tensor * ggml_rms_norm_impl(
3168        struct ggml_context * ctx,
3169        struct ggml_tensor  * a,
3170        float                 eps,
3171        bool                  inplace) {
3172    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
3173
3174    ggml_set_op_params(result, &eps, sizeof(eps));
3175
3176    result->op     = GGML_OP_RMS_NORM;
3177    result->src[0] = a;
3178
3179    return result;
3180}
3181
3182struct ggml_tensor * ggml_rms_norm(
3183        struct ggml_context * ctx,
3184        struct ggml_tensor  * a,
3185        float                 eps) {
3186    return ggml_rms_norm_impl(ctx, a, eps, false);
3187}
3188
3189struct ggml_tensor * ggml_rms_norm_inplace(
3190        struct ggml_context * ctx,
3191        struct ggml_tensor  * a,
3192        float                 eps) {
3193    return ggml_rms_norm_impl(ctx, a, eps, true);
3194}
3195
3196// ggml_rms_norm_back
3197
3198struct ggml_tensor * ggml_rms_norm_back(
3199        struct ggml_context * ctx,
3200        struct ggml_tensor  * a,
3201        struct ggml_tensor  * b,
3202        float                 eps) {
3203    struct ggml_tensor * result = ggml_dup_tensor(ctx, a);
3204
3205    ggml_set_op_params(result, &eps, sizeof(eps));
3206
3207    result->op     = GGML_OP_RMS_NORM_BACK;
3208    result->src[0] = a;
3209    result->src[1] = b;
3210
3211    return result;
3212}
3213
3214// ggml_group_norm
3215
3216static struct ggml_tensor * ggml_group_norm_impl(
3217        struct ggml_context * ctx,
3218        struct ggml_tensor  * a,
3219        int                   n_groups,
3220        float                 eps,
3221        bool                  inplace) {
3222    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
3223
3224    ggml_set_op_params_i32(result, 0, n_groups);
3225    ggml_set_op_params_f32(result, 1, eps);
3226
3227    result->op     = GGML_OP_GROUP_NORM;
3228    result->src[0] = a;
3229
3230    return result;
3231}
3232
3233struct ggml_tensor * ggml_group_norm(
3234        struct ggml_context * ctx,
3235        struct ggml_tensor  * a,
3236        int                   n_groups,
3237        float                 eps) {
3238    return ggml_group_norm_impl(ctx, a, n_groups, eps, false);
3239}
3240
3241struct ggml_tensor * ggml_group_norm_inplace(
3242        struct ggml_context * ctx,
3243        struct ggml_tensor  * a,
3244        int                   n_groups,
3245        float                 eps) {
3246    return ggml_group_norm_impl(ctx, a, n_groups, eps, true);
3247}
3248
3249// ggml_l2_norm
3250
3251static struct ggml_tensor * ggml_l2_norm_impl(
3252        struct ggml_context * ctx,
3253        struct ggml_tensor  * a,
3254        float                 eps,
3255        bool                  inplace) {
3256    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
3257
3258    ggml_set_op_params_f32(result, 0, eps);
3259
3260    result->op     = GGML_OP_L2_NORM;
3261    result->src[0] = a;
3262
3263    return result;
3264}
3265
3266struct ggml_tensor * ggml_l2_norm(
3267        struct ggml_context * ctx,
3268        struct ggml_tensor  * a,
3269        float                 eps) {
3270    return ggml_l2_norm_impl(ctx, a, eps, false);
3271}
3272
3273struct ggml_tensor * ggml_l2_norm_inplace(
3274        struct ggml_context * ctx,
3275        struct ggml_tensor  * a,
3276        float                 eps) {
3277    return ggml_l2_norm_impl(ctx, a, eps, true);
3278}
3279
3280// ggml_prec
3281
3282bool ggml_prec_set_acc(
3283        struct ggml_tensor * a,
3284        enum ggml_prec       prec) {
3285    switch (a->op) {
3286        case GGML_OP_MUL_MAT:
3287        case GGML_OP_MUL_MAT_ID:
3288            {
3289                const int32_t prec_i32 = (int32_t) prec;
3290                ggml_set_op_params_i32(a, 0, prec_i32);
3291            }
3292            break;
3293        case GGML_OP_FLASH_ATTN_EXT:
3294            {
3295                const int32_t prec_i32 = (int32_t) prec;
3296                ggml_set_op_params_i32(a, 3, prec_i32);
3297            }
3298            break;
3299        default:
3300            return false;
3301    };
3302
3303    return true;
3304}
3305
3306bool ggml_prec_set_src(
3307        struct ggml_tensor * a,
3308        enum ggml_prec       prec,
3309        int                  idx) {
3310    GGML_ASSERT(idx >= 0 && idx < GGML_MAX_SRC);
3311
3312    switch (a->op) {
3313        case GGML_OP_MUL_MAT:
3314        case GGML_OP_MUL_MAT_ID:
3315            {
3316                if (idx != 1) {
3317                    return false;
3318                }
3319
3320                const int32_t prec_i32 = (int32_t) prec;
3321                ggml_set_op_params_i32(a, 2 + idx, prec_i32);
3322            }
3323            break;
3324        default:
3325            return false;
3326    };
3327
3328    return true;
3329}
3330
3331// ggml_mul_mat
3332
3333static inline bool ggml_can_mul_mat(const struct ggml_tensor * t0, const struct ggml_tensor * t1) {
3334    static_assert(GGML_MAX_DIMS == 4, "GGML_MAX_DIMS is not 4 - update this function");
3335
3336    return (t0->ne[0]           == t1->ne[0])  &&
3337           (t1->ne[2]%t0->ne[2] == 0)          && // verify t0 is broadcastable
3338           (t1->ne[3]%t0->ne[3] == 0);
3339}
3340
3341struct ggml_tensor * ggml_mul_mat(
3342        struct ggml_context * ctx,
3343        struct ggml_tensor  * a,
3344        struct ggml_tensor  * b) {
3345    GGML_ASSERT(ggml_can_mul_mat(a, b));
3346    GGML_ASSERT(!ggml_is_transposed(a));
3347
3348    const int64_t ne[4] = { a->ne[1], b->ne[1], b->ne[2], b->ne[3] };
3349    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
3350
3351    result->op     = GGML_OP_MUL_MAT;
3352    result->src[0] = a;
3353    result->src[1] = b;
3354
3355    return result;
3356}
3357
3358void ggml_mul_mat_set_prec(
3359        struct ggml_tensor * a,
3360        enum ggml_prec       prec) {
3361    GGML_ASSERT(a->op == GGML_OP_MUL_MAT);
3362
3363    const int32_t prec_i32 = (int32_t) prec;
3364
3365    ggml_set_op_params_i32(a, 0, prec_i32);
3366}
3367
3368void ggml_mul_mat_set_hint(
3369        struct ggml_tensor * a,
3370        enum ggml_op_hint    hint) {
3371    GGML_ASSERT(a->op == GGML_OP_MUL_MAT);
3372
3373    const int32_t hint_i32 = (int32_t) hint;
3374
3375    ggml_set_op_params_i32(a, 1, hint_i32);
3376}
3377
3378// ggml_mul_mat_id
3379
3380/*
3381    c = ggml_mul_mat_id(ctx, as, b, ids);
3382
3383    as  -> [cols, rows, n_expert]
3384    b   -> [cols, n_expert_used, n_tokens]
3385    ids -> [n_expert_used, n_tokens] (i32)
3386    c   -> [rows, n_expert_used, n_tokens]
3387
3388    in b, n_expert_used can be broadcasted to match the n_expert_used of ids
3389
3390    c ~= as[:,:,i] @ b[:,i%r,t], i = ids[e,t] for all e,t in ids
3391*/
3392struct ggml_tensor * ggml_mul_mat_id(
3393        struct ggml_context * ctx,
3394        struct ggml_tensor  * as,
3395        struct ggml_tensor  * b,
3396        struct ggml_tensor  * ids) {
3397    GGML_ASSERT(!ggml_is_transposed(as));
3398    GGML_ASSERT(ids->type == GGML_TYPE_I32);
3399
3400    GGML_ASSERT(as->ne[3] == 1); // as is 3d (one matrix per expert)
3401    GGML_ASSERT(b->ne[3] == 1); // b is 3d
3402    GGML_ASSERT(ids->ne[2] == 1 && ids->ne[3] == 1); // ids is 2d
3403    GGML_ASSERT(ids->ne[1] == b->ne[2]); // must have an expert list per b row
3404    GGML_ASSERT(as->ne[0] == b->ne[0]); // can_mul_mat
3405    GGML_ASSERT(ids->ne[0] % b->ne[1] == 0); // can broadcast
3406
3407    const int64_t ne[4] = { as->ne[1], ids->ne[0], b->ne[2], 1 };
3408    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
3409
3410    result->op     = GGML_OP_MUL_MAT_ID;
3411    result->src[0] = as;
3412    result->src[1] = b;
3413    result->src[2] = ids;
3414
3415    return result;
3416}
3417
3418// ggml_out_prod
3419
3420static inline bool ggml_can_out_prod(const struct ggml_tensor * t0, const struct ggml_tensor * t1) {
3421    static_assert(GGML_MAX_DIMS == 4, "GGML_MAX_DIMS is not 4 - update this function");
3422
3423    return (t0->ne[1] == t1->ne[1])   &&
3424           (t1->ne[2]%t0->ne[2] == 0) && // verify t0 is broadcastable
3425           (t1->ne[3]%t0->ne[3] == 0);
3426}
3427
3428struct ggml_tensor * ggml_out_prod(
3429        struct ggml_context * ctx,
3430        struct ggml_tensor  * a,
3431        struct ggml_tensor  * b) {
3432    GGML_ASSERT(ggml_can_out_prod(a, b));
3433    GGML_ASSERT(!ggml_is_transposed(a));
3434
3435    // a is broadcastable to b for ne[2] and ne[3] -> use b->ne[2] and b->ne[3]
3436    const int64_t ne[4] = { a->ne[0], b->ne[0], b->ne[2], b->ne[3] };
3437    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
3438
3439    result->op     = GGML_OP_OUT_PROD;
3440    result->src[0] = a;
3441    result->src[1] = b;
3442
3443    return result;
3444}
3445
3446// ggml_scale
3447
3448static struct ggml_tensor * ggml_scale_impl(
3449        struct ggml_context * ctx,
3450        struct ggml_tensor  * a,
3451        float                 s,
3452        float                 b,
3453        bool                  inplace) {
3454    GGML_ASSERT(ggml_is_padded_1d(a));
3455
3456    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
3457
3458    float params[2] = { s, b };
3459    ggml_set_op_params(result, &params, sizeof(params));
3460
3461    result->op     = GGML_OP_SCALE;
3462    result->src[0] = a;
3463
3464    return result;
3465}
3466
3467struct ggml_tensor * ggml_scale(
3468        struct ggml_context * ctx,
3469        struct ggml_tensor  * a,
3470        float                 s) {
3471    return ggml_scale_impl(ctx, a, s, 0.0, false);
3472}
3473
3474struct ggml_tensor * ggml_scale_inplace(
3475        struct ggml_context * ctx,
3476        struct ggml_tensor  * a,
3477        float                 s) {
3478    return ggml_scale_impl(ctx, a, s, 0.0, true);
3479}
3480
3481struct ggml_tensor * ggml_scale_bias(
3482        struct ggml_context * ctx,
3483        struct ggml_tensor  * a,
3484        float                 s,
3485        float                 b) {
3486    return ggml_scale_impl(ctx, a, s, b, false);
3487}
3488
3489struct ggml_tensor * ggml_scale_bias_inplace(
3490        struct ggml_context * ctx,
3491        struct ggml_tensor  * a,
3492        float                 s,
3493        float                 b) {
3494    return ggml_scale_impl(ctx, a, s, b, true);
3495}
3496
3497// ggml_set
3498
3499static struct ggml_tensor * ggml_set_impl(
3500        struct ggml_context * ctx,
3501        struct ggml_tensor  * a,
3502        struct ggml_tensor  * b,
3503        size_t                nb1,
3504        size_t                nb2,
3505        size_t                nb3,
3506        size_t                offset,
3507        bool                  inplace) {
3508    GGML_ASSERT(ggml_nelements(a) >= ggml_nelements(b));
3509
3510    // make a view of the destination
3511    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
3512
3513    GGML_ASSERT(offset < (size_t)(1 << 30));
3514    int32_t params[] = { nb1, nb2, nb3, offset, inplace ? 1 : 0 };
3515    ggml_set_op_params(result, params, sizeof(params));
3516
3517    result->op     = GGML_OP_SET;
3518    result->src[0] = a;
3519    result->src[1] = b;
3520
3521    return result;
3522}
3523
3524struct ggml_tensor * ggml_set(
3525        struct ggml_context * ctx,
3526        struct ggml_tensor  * a,
3527        struct ggml_tensor  * b,
3528        size_t                nb1,
3529        size_t                nb2,
3530        size_t                nb3,
3531        size_t                offset) {
3532    return ggml_set_impl(ctx, a, b, nb1, nb2, nb3, offset, false);
3533}
3534
3535struct ggml_tensor * ggml_set_inplace(
3536        struct ggml_context * ctx,
3537        struct ggml_tensor  * a,
3538        struct ggml_tensor  * b,
3539        size_t                nb1,
3540        size_t                nb2,
3541        size_t                nb3,
3542        size_t                offset) {
3543    return ggml_set_impl(ctx, a, b, nb1, nb2, nb3, offset, true);
3544}
3545
3546struct ggml_tensor * ggml_set_1d(
3547        struct ggml_context * ctx,
3548        struct ggml_tensor  * a,
3549        struct ggml_tensor  * b,
3550        size_t                offset) {
3551    return ggml_set_impl(ctx, a, b, a->nb[1], a->nb[2], a->nb[3], offset, false);
3552}
3553
3554struct ggml_tensor * ggml_set_1d_inplace(
3555        struct ggml_context * ctx,
3556        struct ggml_tensor  * a,
3557        struct ggml_tensor  * b,
3558        size_t                offset) {
3559    return ggml_set_impl(ctx, a, b, a->nb[1], a->nb[2], a->nb[3], offset, true);
3560}
3561
3562struct ggml_tensor * ggml_set_2d(
3563        struct ggml_context * ctx,
3564        struct ggml_tensor  * a,
3565        struct ggml_tensor  * b,
3566        size_t                nb1,
3567        size_t                offset) {
3568    return ggml_set_impl(ctx, a, b, nb1, a->nb[2], a->nb[3], offset, false);
3569}
3570
3571struct ggml_tensor * ggml_set_2d_inplace(
3572        struct ggml_context * ctx,
3573        struct ggml_tensor  * a,
3574        struct ggml_tensor  * b,
3575        size_t                nb1,
3576        size_t                offset) {
3577    return ggml_set_impl(ctx, a, b, nb1, a->nb[2], a->nb[3], offset, true);
3578}
3579
3580// ggml_cpy
3581
3582static struct ggml_tensor * ggml_cpy_impl(
3583        struct ggml_context * ctx,
3584        struct ggml_tensor  * a,
3585        struct ggml_tensor  * b) {
3586    GGML_ASSERT(ggml_nelements(a) == ggml_nelements(b));
3587
3588    // make a view of the destination
3589    struct ggml_tensor * result = ggml_view_tensor(ctx, b);
3590    if (strlen(b->name) > 0) {
3591        ggml_format_name(result, "%s (copy of %s)", b->name, a->name);
3592    } else {
3593        ggml_format_name(result, "%s (copy)", a->name);
3594    }
3595
3596    result->op     = GGML_OP_CPY;
3597    result->src[0] = a;
3598    result->src[1] = b;
3599
3600    return result;
3601}
3602
3603struct ggml_tensor * ggml_cpy(
3604        struct ggml_context * ctx,
3605        struct ggml_tensor * a,
3606        struct ggml_tensor * b) {
3607    return ggml_cpy_impl(ctx, a, b);
3608}
3609
3610struct ggml_tensor * ggml_cast(
3611        struct ggml_context * ctx,
3612        struct ggml_tensor  * a,
3613        enum   ggml_type      type) {
3614    struct ggml_tensor * result = ggml_new_tensor(ctx, type, GGML_MAX_DIMS, a->ne);
3615    ggml_format_name(result, "%s (copy)", a->name);
3616
3617    result->op     = GGML_OP_CPY;
3618    result->src[0] = a;
3619    result->src[1] = result; // note: this self-reference might seem redundant, but it's actually needed by some
3620                             //       backends for consistency with ggml_cpy_impl() above
3621
3622    return result;
3623}
3624
3625// ggml_cont
3626
3627static struct ggml_tensor * ggml_cont_impl(
3628        struct ggml_context * ctx,
3629        struct ggml_tensor  * a) {
3630    struct ggml_tensor * result = ggml_dup_tensor(ctx, a);
3631    ggml_format_name(result, "%s (cont)", a->name);
3632
3633    result->op     = GGML_OP_CONT;
3634    result->src[0] = a;
3635
3636    return result;
3637}
3638
3639struct ggml_tensor * ggml_cont(
3640        struct ggml_context * ctx,
3641        struct ggml_tensor * a) {
3642    return ggml_cont_impl(ctx, a);
3643}
3644
3645// make contiguous, with new shape
3646GGML_API struct ggml_tensor * ggml_cont_1d(
3647        struct ggml_context * ctx,
3648        struct ggml_tensor  * a,
3649        int64_t               ne0) {
3650    return ggml_cont_4d(ctx, a, ne0, 1, 1, 1);
3651}
3652
3653GGML_API struct ggml_tensor * ggml_cont_2d(
3654        struct ggml_context * ctx,
3655        struct ggml_tensor  * a,
3656        int64_t               ne0,
3657        int64_t               ne1) {
3658    return ggml_cont_4d(ctx, a, ne0, ne1, 1, 1);
3659}
3660
3661GGML_API struct ggml_tensor * ggml_cont_3d(
3662        struct ggml_context * ctx,
3663        struct ggml_tensor  * a,
3664        int64_t               ne0,
3665        int64_t               ne1,
3666        int64_t               ne2) {
3667    return ggml_cont_4d(ctx, a, ne0, ne1, ne2, 1);
3668}
3669
3670struct ggml_tensor * ggml_cont_4d(
3671        struct ggml_context * ctx,
3672        struct ggml_tensor  * a,
3673        int64_t               ne0,
3674        int64_t               ne1,
3675        int64_t               ne2,
3676        int64_t               ne3) {
3677    GGML_ASSERT(ggml_nelements(a) == (ne0*ne1*ne2*ne3));
3678
3679    struct ggml_tensor * result = ggml_new_tensor_4d(ctx, a->type, ne0, ne1, ne2, ne3);
3680    ggml_format_name(result, "%s (cont)", a->name);
3681
3682    result->op     = GGML_OP_CONT;
3683    result->src[0] = a;
3684
3685    return result;
3686}
3687
3688// ggml_reshape
3689
3690struct ggml_tensor * ggml_reshape(
3691        struct ggml_context * ctx,
3692        struct ggml_tensor * a,
3693        struct ggml_tensor * b) {
3694    GGML_ASSERT(ggml_is_contiguous(a));
3695    // as only the shape of b is relevant, and not its memory layout, b is allowed to be non contiguous.
3696    GGML_ASSERT(ggml_nelements(a) == ggml_nelements(b));
3697
3698    struct ggml_tensor * result = ggml_new_tensor_impl(ctx, a->type, GGML_MAX_DIMS, b->ne, a, 0);
3699    ggml_format_name(result, "%s (reshaped)", a->name);
3700
3701    result->op     = GGML_OP_RESHAPE;
3702    result->src[0] = a;
3703
3704    return result;
3705}
3706
3707struct ggml_tensor * ggml_reshape_1d(
3708        struct ggml_context * ctx,
3709        struct ggml_tensor  * a,
3710        int64_t               ne0) {
3711    GGML_ASSERT(ggml_is_contiguous(a));
3712    GGML_ASSERT(ggml_nelements(a) == ne0);
3713
3714    const int64_t ne[1] = { ne0 };
3715    struct ggml_tensor * result = ggml_new_tensor_impl(ctx, a->type, 1, ne, a, 0);
3716    ggml_format_name(result, "%s (reshaped)", a->name);
3717
3718    result->op     = GGML_OP_RESHAPE;
3719    result->src[0] = a;
3720
3721    return result;
3722}
3723
3724struct ggml_tensor * ggml_reshape_2d(
3725        struct ggml_context * ctx,
3726        struct ggml_tensor  * a,
3727        int64_t               ne0,
3728        int64_t               ne1) {
3729    GGML_ASSERT(ggml_is_contiguous(a));
3730    GGML_ASSERT(ggml_nelements(a) == ne0*ne1);
3731
3732    const int64_t ne[2] = { ne0, ne1 };
3733    struct ggml_tensor * result = ggml_new_tensor_impl(ctx, a->type, 2, ne, a, 0);
3734    ggml_format_name(result, "%s (reshaped)", a->name);
3735
3736    result->op     = GGML_OP_RESHAPE;
3737    result->src[0] = a;
3738
3739    return result;
3740}
3741
3742struct ggml_tensor * ggml_reshape_3d(
3743        struct ggml_context * ctx,
3744        struct ggml_tensor  * a,
3745        int64_t               ne0,
3746        int64_t               ne1,
3747        int64_t               ne2) {
3748    GGML_ASSERT(ggml_is_contiguous(a));
3749    GGML_ASSERT(ggml_nelements(a) == ne0*ne1*ne2);
3750
3751    const int64_t ne[3] = { ne0, ne1, ne2 };
3752    struct ggml_tensor * result = ggml_new_tensor_impl(ctx, a->type, 3, ne, a, 0);
3753    ggml_format_name(result, "%s (reshaped)", a->name);
3754
3755    result->op     = GGML_OP_RESHAPE;
3756    result->src[0] = a;
3757
3758    return result;
3759}
3760
3761struct ggml_tensor * ggml_reshape_4d(
3762        struct ggml_context * ctx,
3763        struct ggml_tensor  * a,
3764        int64_t               ne0,
3765        int64_t               ne1,
3766        int64_t               ne2,
3767        int64_t               ne3) {
3768    GGML_ASSERT(ggml_is_contiguous(a));
3769    GGML_ASSERT(ggml_nelements(a) == ne0*ne1*ne2*ne3);
3770
3771    const int64_t ne[4] = { ne0, ne1, ne2, ne3 };
3772    struct ggml_tensor * result = ggml_new_tensor_impl(ctx, a->type, 4, ne, a, 0);
3773    ggml_format_name(result, "%s (reshaped)", a->name);
3774
3775    result->op     = GGML_OP_RESHAPE;
3776    result->src[0] = a;
3777
3778    return result;
3779}
3780
3781static struct ggml_tensor * ggml_view_impl(
3782        struct ggml_context * ctx,
3783        struct ggml_tensor  * a,
3784        int                   n_dims,
3785        const int64_t       * ne,
3786        size_t                offset) {
3787    struct ggml_tensor * result = ggml_new_tensor_impl(ctx, a->type, n_dims, ne, a, offset);
3788    ggml_format_name(result, "%s (view)", a->name);
3789
3790    ggml_set_op_params(result, &offset, sizeof(offset));
3791
3792    result->op     = GGML_OP_VIEW;
3793    result->src[0] = a;
3794
3795    return result;
3796}
3797
3798// ggml_view_1d
3799
3800struct ggml_tensor * ggml_view_1d(
3801        struct ggml_context * ctx,
3802        struct ggml_tensor  * a,
3803        int64_t               ne0,
3804        size_t                offset) {
3805    struct ggml_tensor * result = ggml_view_impl(ctx, a, 1, &ne0, offset);
3806
3807    return result;
3808}
3809
3810// ggml_view_2d
3811
3812struct ggml_tensor * ggml_view_2d(
3813        struct ggml_context * ctx,
3814        struct ggml_tensor  * a,
3815        int64_t               ne0,
3816        int64_t               ne1,
3817        size_t                nb1,
3818        size_t                offset) {
3819    const int64_t ne[2] = { ne0, ne1 };
3820
3821    struct ggml_tensor * result = ggml_view_impl(ctx, a, 2, ne, offset);
3822
3823    result->nb[1] = nb1;
3824    result->nb[2] = result->nb[1]*ne1;
3825    result->nb[3] = result->nb[2];
3826
3827    return result;
3828}
3829
3830// ggml_view_3d
3831
3832struct ggml_tensor * ggml_view_3d(
3833        struct ggml_context * ctx,
3834        struct ggml_tensor  * a,
3835        int64_t               ne0,
3836        int64_t               ne1,
3837        int64_t               ne2,
3838        size_t                nb1,
3839        size_t                nb2,
3840        size_t                offset) {
3841    const int64_t ne[3] = { ne0, ne1, ne2 };
3842
3843    struct ggml_tensor * result = ggml_view_impl(ctx, a, 3, ne, offset);
3844
3845    result->nb[1] = nb1;
3846    result->nb[2] = nb2;
3847    result->nb[3] = result->nb[2]*ne2;
3848
3849    return result;
3850}
3851
3852// ggml_view_4d
3853
3854struct ggml_tensor * ggml_view_4d(
3855        struct ggml_context * ctx,
3856        struct ggml_tensor  * a,
3857        int64_t               ne0,
3858        int64_t               ne1,
3859        int64_t               ne2,
3860        int64_t               ne3,
3861        size_t                nb1,
3862        size_t                nb2,
3863        size_t                nb3,
3864        size_t                offset) {
3865    const int64_t ne[4] = { ne0, ne1, ne2, ne3 };
3866
3867    struct ggml_tensor * result = ggml_view_impl(ctx, a, 4, ne, offset);
3868
3869    result->nb[1] = nb1;
3870    result->nb[2] = nb2;
3871    result->nb[3] = nb3;
3872
3873    return result;
3874}
3875
3876// ggml_permute
3877
3878struct ggml_tensor * ggml_permute(
3879        struct ggml_context * ctx,
3880        struct ggml_tensor  * a,
3881        int                   axis0,
3882        int                   axis1,
3883        int                   axis2,
3884        int                   axis3) {
3885    GGML_ASSERT(axis0 >= 0 && axis0 < GGML_MAX_DIMS);
3886    GGML_ASSERT(axis1 >= 0 && axis1 < GGML_MAX_DIMS);
3887    GGML_ASSERT(axis2 >= 0 && axis2 < GGML_MAX_DIMS);
3888    GGML_ASSERT(axis3 >= 0 && axis3 < GGML_MAX_DIMS);
3889
3890    GGML_ASSERT(axis0 != axis1);
3891    GGML_ASSERT(axis0 != axis2);
3892    GGML_ASSERT(axis0 != axis3);
3893    GGML_ASSERT(axis1 != axis2);
3894    GGML_ASSERT(axis1 != axis3);
3895    GGML_ASSERT(axis2 != axis3);
3896
3897    struct ggml_tensor * result = ggml_view_tensor(ctx, a);
3898    ggml_format_name(result, "%s (permuted)", a->name);
3899
3900    int ne[GGML_MAX_DIMS];
3901    int nb[GGML_MAX_DIMS];
3902
3903    ne[axis0] = a->ne[0];
3904    ne[axis1] = a->ne[1];
3905    ne[axis2] = a->ne[2];
3906    ne[axis3] = a->ne[3];
3907
3908    nb[axis0] = a->nb[0];
3909    nb[axis1] = a->nb[1];
3910    nb[axis2] = a->nb[2];
3911    nb[axis3] = a->nb[3];
3912
3913    result->ne[0] = ne[0];
3914    result->ne[1] = ne[1];
3915    result->ne[2] = ne[2];
3916    result->ne[3] = ne[3];
3917
3918    result->nb[0] = nb[0];
3919    result->nb[1] = nb[1];
3920    result->nb[2] = nb[2];
3921    result->nb[3] = nb[3];
3922
3923    result->op     = GGML_OP_PERMUTE;
3924    result->src[0] = a;
3925
3926    int32_t params[] = { axis0, axis1, axis2, axis3 };
3927    ggml_set_op_params(result, params, sizeof(params));
3928
3929    return result;
3930}
3931
3932// ggml_transpose
3933
3934struct ggml_tensor * ggml_transpose(
3935        struct ggml_context * ctx,
3936        struct ggml_tensor  * a) {
3937    struct ggml_tensor * result = ggml_view_tensor(ctx, a);
3938    ggml_format_name(result, "%s (transposed)", a->name);
3939
3940    result->ne[0] = a->ne[1];
3941    result->ne[1] = a->ne[0];
3942
3943    result->nb[0] = a->nb[1];
3944    result->nb[1] = a->nb[0];
3945
3946    result->op     = GGML_OP_TRANSPOSE;
3947    result->src[0] = a;
3948
3949    return result;
3950}
3951
3952// ggml_get_rows
3953
3954struct ggml_tensor * ggml_get_rows(
3955        struct ggml_context * ctx,
3956        struct ggml_tensor  * a,
3957        struct ggml_tensor  * b) {
3958    GGML_ASSERT(a->ne[2] == b->ne[1]);
3959    GGML_ASSERT(a->ne[3] == b->ne[2]);
3960    GGML_ASSERT(b->ne[3] == 1);
3961    GGML_ASSERT(b->type == GGML_TYPE_I32);
3962
3963    // TODO: implement non F32 return
3964    enum ggml_type type = GGML_TYPE_F32;
3965    if (a->type == GGML_TYPE_I32) {
3966        type = a->type;
3967    }
3968    struct ggml_tensor * result = ggml_new_tensor_4d(ctx, type, a->ne[0], b->ne[0], b->ne[1], b->ne[2]);
3969
3970    result->op     = GGML_OP_GET_ROWS;
3971    result->src[0] = a;
3972    result->src[1] = b;
3973
3974    return result;
3975}
3976
3977// ggml_get_rows_back
3978
3979struct ggml_tensor * ggml_get_rows_back(
3980        struct ggml_context * ctx,
3981        struct ggml_tensor  * a,
3982        struct ggml_tensor  * b,
3983        struct ggml_tensor  * c) {
3984    GGML_ASSERT(ggml_is_matrix(a) && ggml_is_vector(b) && b->type == GGML_TYPE_I32);
3985    GGML_ASSERT(ggml_is_matrix(c) && (a->ne[0] == c->ne[0]));
3986
3987    // TODO: implement non F32 return
3988    //struct ggml_tensor * result = ggml_new_tensor_2d(ctx, a->type, a->ne[0], b->ne[0]);
3989    struct ggml_tensor * result = ggml_new_tensor_2d(ctx, GGML_TYPE_F32, c->ne[0], c->ne[1]);
3990
3991    result->op     = GGML_OP_GET_ROWS_BACK;
3992    result->src[0] = a;
3993    result->src[1] = b;
3994
3995    return result;
3996}
3997
3998// ggml_set_rows
3999
4000struct ggml_tensor * ggml_set_rows(
4001        struct ggml_context * ctx,
4002        struct ggml_tensor  * a,
4003        struct ggml_tensor  * b,
4004        struct ggml_tensor  * c) {
4005    GGML_ASSERT(a->ne[0] == b->ne[0]);
4006    GGML_ASSERT(a->ne[2] == b->ne[2]);
4007    GGML_ASSERT(a->ne[3] == b->ne[3]);
4008    GGML_ASSERT(b->ne[1] == c->ne[0]);
4009    GGML_ASSERT(b->ne[2] % c->ne[1] == 0);
4010    GGML_ASSERT(b->ne[3] % c->ne[2] == 0);
4011    GGML_ASSERT(c->ne[3] == 1);
4012    GGML_ASSERT(b->type == GGML_TYPE_F32 || b->type == GGML_TYPE_F16);
4013    GGML_ASSERT(c->type == GGML_TYPE_I64 || c->type == GGML_TYPE_I32);
4014
4015    GGML_ASSERT(ggml_is_contiguous_rows(a));
4016    GGML_ASSERT(ggml_is_contiguous_rows(b));
4017
4018    struct ggml_tensor * result = ggml_view_tensor(ctx, a);
4019
4020    result->op     = GGML_OP_SET_ROWS;
4021    result->src[0] = b;
4022    result->src[1] = c;
4023    result->src[2] = a; // note: order is weird due to legacy reasons (https://github.com/ggml-org/llama.cpp/pull/16063#discussion_r2385795931)
4024
4025    return result;
4026}
4027
4028// ggml_diag
4029
4030struct ggml_tensor * ggml_diag(
4031        struct ggml_context * ctx,
4032        struct ggml_tensor  * a) {
4033    GGML_ASSERT(a->ne[1] == 1);
4034
4035    const int64_t ne[4] = { a->ne[0], a->ne[0], a->ne[2], a->ne[3] };
4036    struct ggml_tensor * result = ggml_new_tensor(ctx, a->type, 4, ne);
4037
4038    result->op     = GGML_OP_DIAG;
4039    result->src[0] = a;
4040
4041    return result;
4042}
4043
4044// ggml_diag_mask_inf
4045
4046static struct ggml_tensor * ggml_diag_mask_inf_impl(
4047        struct ggml_context * ctx,
4048        struct ggml_tensor  * a,
4049        int                   n_past,
4050        bool                  inplace) {
4051    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
4052
4053    int32_t params[] = { n_past };
4054    ggml_set_op_params(result, params, sizeof(params));
4055
4056    result->op     = GGML_OP_DIAG_MASK_INF;
4057    result->src[0] = a;
4058
4059    return result;
4060}
4061
4062struct ggml_tensor * ggml_diag_mask_inf(
4063        struct ggml_context * ctx,
4064        struct ggml_tensor  * a,
4065        int                   n_past) {
4066    return ggml_diag_mask_inf_impl(ctx, a, n_past, false);
4067}
4068
4069struct ggml_tensor * ggml_diag_mask_inf_inplace(
4070        struct ggml_context * ctx,
4071        struct ggml_tensor  * a,
4072        int                   n_past) {
4073    return ggml_diag_mask_inf_impl(ctx, a, n_past, true);
4074}
4075
4076// ggml_diag_mask_zero
4077
4078static struct ggml_tensor * ggml_diag_mask_zero_impl(
4079        struct ggml_context * ctx,
4080        struct ggml_tensor  * a,
4081        int                   n_past,
4082        bool                  inplace) {
4083    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
4084
4085    int32_t params[] = { n_past };
4086    ggml_set_op_params(result, params, sizeof(params));
4087
4088    result->op     = GGML_OP_DIAG_MASK_ZERO;
4089    result->src[0] = a;
4090
4091    return result;
4092}
4093
4094struct ggml_tensor * ggml_diag_mask_zero(
4095        struct ggml_context * ctx,
4096        struct ggml_tensor  * a,
4097        int                   n_past) {
4098    return ggml_diag_mask_zero_impl(ctx, a, n_past, false);
4099}
4100
4101struct ggml_tensor * ggml_diag_mask_zero_inplace(
4102        struct ggml_context * ctx,
4103        struct ggml_tensor  * a,
4104        int                   n_past) {
4105    return ggml_diag_mask_zero_impl(ctx, a, n_past, true);
4106}
4107
4108// ggml_clamp
4109
4110static struct ggml_tensor * ggml_clamp_impl(
4111        struct ggml_context * ctx,
4112        struct ggml_tensor  * a,
4113        float                 min,
4114        float                 max,
4115        bool                  inplace) {
4116    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
4117
4118    float params[] = { min, max };
4119    ggml_set_op_params(result, params, sizeof(params));
4120
4121    result->op     = GGML_OP_CLAMP;
4122    result->src[0] = a;
4123
4124    return result;
4125}
4126
4127struct ggml_tensor * ggml_clamp(
4128    struct ggml_context * ctx,
4129    struct ggml_tensor  * a,
4130    float                 min,
4131    float                 max) {
4132    return ggml_clamp_impl(ctx, a, min, max, false);
4133}
4134
4135struct ggml_tensor * ggml_clamp_inplace(
4136    struct ggml_context * ctx,
4137    struct ggml_tensor  * a,
4138    float                 min,
4139    float                 max) {
4140    return ggml_clamp_impl(ctx, a, min, max, true);
4141}
4142
4143// ggml_soft_max
4144
4145static struct ggml_tensor * ggml_soft_max_impl(
4146        struct ggml_context * ctx,
4147        struct ggml_tensor  * a,
4148        struct ggml_tensor  * mask,
4149        float                 scale,
4150        float                 max_bias,
4151        bool                  inplace) {
4152    GGML_ASSERT(ggml_is_contiguous(a));
4153
4154    if (mask) {
4155        GGML_ASSERT(mask->type == GGML_TYPE_F16 || mask->type == GGML_TYPE_F32);
4156        GGML_ASSERT(ggml_is_contiguous(mask));
4157        GGML_ASSERT(mask->ne[0] == a->ne[0]);
4158        GGML_ASSERT(mask->ne[1] >= a->ne[1]);
4159        GGML_ASSERT(a->ne[2]%mask->ne[2] == 0);
4160        GGML_ASSERT(a->ne[3]%mask->ne[3] == 0);
4161    }
4162
4163    if (max_bias > 0.0f) {
4164        GGML_ASSERT(mask);
4165    }
4166
4167    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
4168
4169    float params[] = { scale, max_bias };
4170    ggml_set_op_params(result, params, sizeof(params));
4171
4172    result->op     = GGML_OP_SOFT_MAX;
4173    result->src[0] = a;
4174    result->src[1] = mask;
4175
4176    return result;
4177}
4178
4179struct ggml_tensor * ggml_soft_max(
4180        struct ggml_context * ctx,
4181        struct ggml_tensor  * a) {
4182    return ggml_soft_max_impl(ctx, a, NULL, 1.0f, 0.0f, false);
4183}
4184
4185struct ggml_tensor * ggml_soft_max_inplace(
4186        struct ggml_context * ctx,
4187        struct ggml_tensor  * a) {
4188    return ggml_soft_max_impl(ctx, a, NULL, 1.0f, 0.0f, true);
4189}
4190
4191struct ggml_tensor * ggml_soft_max_ext(
4192        struct ggml_context * ctx,
4193        struct ggml_tensor  * a,
4194        struct ggml_tensor  * mask,
4195        float                 scale,
4196        float                 max_bias) {
4197    return ggml_soft_max_impl(ctx, a, mask, scale, max_bias, false);
4198}
4199
4200struct ggml_tensor * ggml_soft_max_ext_inplace(
4201        struct ggml_context * ctx,
4202        struct ggml_tensor  * a,
4203        struct ggml_tensor  * mask,
4204        float                 scale,
4205        float                 max_bias) {
4206    return ggml_soft_max_impl(ctx, a, mask, scale, max_bias, true);
4207}
4208
4209void ggml_soft_max_add_sinks(
4210        struct ggml_tensor * a,
4211        struct ggml_tensor * sinks) {
4212    if (!sinks) {
4213        a->src[2] = NULL;
4214        return;
4215    }
4216
4217    GGML_ASSERT(a->op == GGML_OP_SOFT_MAX);
4218    GGML_ASSERT(a->src[2] == NULL);
4219    GGML_ASSERT(a->src[0]->ne[2] == sinks->ne[0]);
4220    GGML_ASSERT(sinks->type == GGML_TYPE_F32);
4221
4222    a->src[2] = sinks;
4223}
4224
4225// ggml_soft_max_ext_back
4226
4227static struct ggml_tensor * ggml_soft_max_ext_back_impl(
4228        struct ggml_context * ctx,
4229        struct ggml_tensor  * a,
4230        struct ggml_tensor  * b,
4231        float                 scale,
4232        float                 max_bias,
4233        bool                  inplace) {
4234    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
4235
4236    result->op     = GGML_OP_SOFT_MAX_BACK;
4237    result->src[0] = a;
4238    result->src[1] = b;
4239
4240    memcpy((float *) result->op_params + 0, &scale,    sizeof(float));
4241    memcpy((float *) result->op_params + 1, &max_bias, sizeof(float));
4242
4243    return result;
4244}
4245
4246struct ggml_tensor * ggml_soft_max_ext_back(
4247        struct ggml_context * ctx,
4248        struct ggml_tensor  * a,
4249        struct ggml_tensor  * b,
4250        float                 scale,
4251        float                 max_bias) {
4252    return ggml_soft_max_ext_back_impl(ctx, a, b, scale, max_bias, false);
4253}
4254
4255struct ggml_tensor * ggml_soft_max_ext_back_inplace(
4256        struct ggml_context * ctx,
4257        struct ggml_tensor  * a,
4258        struct ggml_tensor  * b,
4259        float                 scale,
4260        float                 max_bias) {
4261    return ggml_soft_max_ext_back_impl(ctx, a, b, scale, max_bias, true);
4262}
4263
4264// ggml_rope
4265
4266static struct ggml_tensor * ggml_rope_impl(
4267        struct ggml_context * ctx,
4268        struct ggml_tensor  * a,
4269        struct ggml_tensor  * b,
4270        struct ggml_tensor  * c,
4271        int                   n_dims,
4272        int                   sections[GGML_MROPE_SECTIONS],
4273        int                   mode,
4274        int                   n_ctx_orig,
4275        float                 freq_base,
4276        float                 freq_scale,
4277        float                 ext_factor,
4278        float                 attn_factor,
4279        float                 beta_fast,
4280        float                 beta_slow,
4281        bool                  inplace) {
4282    GGML_ASSERT((mode & 1) == 0 && "mode & 1 == 1 is no longer supported");
4283
4284    GGML_ASSERT(ggml_is_vector(b));
4285    GGML_ASSERT(b->type == GGML_TYPE_I32);
4286
4287    bool mrope_used = mode & GGML_ROPE_TYPE_MROPE;
4288    if (mrope_used) {
4289        GGML_ASSERT(a->ne[2] * 4 == b->ne[0]); // mrope expecting 4 position ids per token
4290    } else {
4291        GGML_ASSERT(a->ne[2] == b->ne[0]);
4292    }
4293
4294    if (c) {
4295        GGML_ASSERT(c->type == GGML_TYPE_F32);
4296        GGML_ASSERT(c->ne[0] >= n_dims / 2);
4297    }
4298
4299    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
4300
4301    int32_t params[16] = { /*n_past*/ 0, n_dims, mode, /*n_ctx*/ 0, n_ctx_orig };
4302    memcpy(params +  5, &freq_base,    sizeof(float));
4303    memcpy(params +  6, &freq_scale,   sizeof(float));
4304    memcpy(params +  7, &ext_factor,   sizeof(float));
4305    memcpy(params +  8, &attn_factor,  sizeof(float));
4306    memcpy(params +  9, &beta_fast,    sizeof(float));
4307    memcpy(params + 10, &beta_slow,    sizeof(float));
4308    if (mrope_used && sections) {
4309        memcpy(params + 11, sections,  sizeof(int32_t) * GGML_MROPE_SECTIONS);
4310    } else {
4311        memset(params + 11, 0,         sizeof(int32_t) * GGML_MROPE_SECTIONS);
4312    }
4313    params[15] = 0; // n_offs, set via ggml_rope_set_offset()
4314
4315    ggml_set_op_params(result, params, sizeof(params));
4316
4317    result->op     = GGML_OP_ROPE;
4318    result->src[0] = a;
4319    result->src[1] = b;
4320    result->src[2] = c;
4321
4322    return result;
4323}
4324
4325struct ggml_tensor * ggml_rope(
4326        struct ggml_context * ctx,
4327        struct ggml_tensor  * a,
4328        struct ggml_tensor  * b,
4329        int                   n_dims,
4330        int                   mode) {
4331    return ggml_rope_impl(
4332        ctx, a, b, NULL, n_dims, NULL, mode, 0, 10000.0f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, false
4333    );
4334}
4335
4336struct ggml_tensor * ggml_rope_multi(
4337        struct ggml_context * ctx,
4338        struct ggml_tensor  * a,
4339        struct ggml_tensor  * b,
4340        struct ggml_tensor  * c,
4341        int                   n_dims,
4342        int                   sections[GGML_MROPE_SECTIONS],
4343        int                   mode,
4344        int                   n_ctx_orig,
4345        float                 freq_base,
4346        float                 freq_scale,
4347        float                 ext_factor,
4348        float                 attn_factor,
4349        float                 beta_fast,
4350        float                 beta_slow) {
4351    return ggml_rope_impl(
4352        ctx, a, b, c, n_dims, sections, mode, n_ctx_orig, freq_base, freq_scale,
4353        ext_factor, attn_factor, beta_fast, beta_slow, false
4354    );
4355}
4356
4357struct ggml_tensor * ggml_rope_multi_inplace(
4358        struct ggml_context * ctx,
4359        struct ggml_tensor  * a,
4360        struct ggml_tensor  * b,
4361        struct ggml_tensor  * c,
4362        int                   n_dims,
4363        int                   sections[GGML_MROPE_SECTIONS],
4364        int                   mode,
4365        int                   n_ctx_orig,
4366        float                 freq_base,
4367        float                 freq_scale,
4368        float                 ext_factor,
4369        float                 attn_factor,
4370        float                 beta_fast,
4371        float                 beta_slow) {
4372    return ggml_rope_impl(
4373        ctx, a, b, c, n_dims, sections, mode, n_ctx_orig, freq_base, freq_scale,
4374        ext_factor, attn_factor, beta_fast, beta_slow, true
4375    );
4376}
4377
4378struct ggml_tensor * ggml_rope_inplace(
4379        struct ggml_context * ctx,
4380        struct ggml_tensor  * a,
4381        struct ggml_tensor  * b,
4382        int                   n_dims,
4383        int                   mode) {
4384    return ggml_rope_impl(
4385        ctx, a, b, NULL, n_dims, NULL, mode, 0, 10000.0f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, true
4386    );
4387}
4388
4389struct ggml_tensor * ggml_rope_ext(
4390        struct ggml_context * ctx,
4391        struct ggml_tensor  * a,
4392        struct ggml_tensor  * b,
4393        struct ggml_tensor  * c,
4394        int                   n_dims,
4395        int                   mode,
4396        int                   n_ctx_orig,
4397        float                 freq_base,
4398        float                 freq_scale,
4399        float                 ext_factor,
4400        float                 attn_factor,
4401        float                 beta_fast,
4402        float                 beta_slow) {
4403    return ggml_rope_impl(
4404        ctx, a, b, c, n_dims, NULL, mode, n_ctx_orig, freq_base, freq_scale,
4405        ext_factor, attn_factor, beta_fast, beta_slow, false
4406    );
4407}
4408
4409struct ggml_tensor * ggml_rope_ext_inplace(
4410        struct ggml_context * ctx,
4411        struct ggml_tensor  * a,
4412        struct ggml_tensor  * b,
4413        struct ggml_tensor  * c,
4414        int                   n_dims,
4415        int                   mode,
4416        int                   n_ctx_orig,
4417        float                 freq_base,
4418        float                 freq_scale,
4419        float                 ext_factor,
4420        float                 attn_factor,
4421        float                 beta_fast,
4422        float                 beta_slow) {
4423    return ggml_rope_impl(
4424        ctx, a, b, c, n_dims, NULL, mode, n_ctx_orig, freq_base, freq_scale,
4425        ext_factor, attn_factor, beta_fast, beta_slow, true
4426    );
4427}
4428
4429struct ggml_tensor * ggml_rope_custom(
4430        struct ggml_context * ctx,
4431        struct ggml_tensor  * a,
4432        struct ggml_tensor  * b,
4433        int                   n_dims,
4434        int                   mode,
4435        int                   n_ctx_orig,
4436        float                 freq_base,
4437        float                 freq_scale,
4438        float                 ext_factor,
4439        float                 attn_factor,
4440        float                 beta_fast,
4441        float                 beta_slow) {
4442    return ggml_rope_impl(
4443        ctx, a, b, NULL, n_dims, NULL, mode, n_ctx_orig, freq_base, freq_scale,
4444        ext_factor, attn_factor, beta_fast, beta_slow, false
4445    );
4446}
4447
4448struct ggml_tensor * ggml_rope_custom_inplace(
4449        struct ggml_context * ctx,
4450        struct ggml_tensor  * a,
4451        struct ggml_tensor  * b,
4452        int                   n_dims,
4453        int                   mode,
4454        int                   n_ctx_orig,
4455        float                 freq_base,
4456        float                 freq_scale,
4457        float                 ext_factor,
4458        float                 attn_factor,
4459        float                 beta_fast,
4460        float                 beta_slow) {
4461    return ggml_rope_impl(
4462        ctx, a, b, NULL, n_dims, NULL, mode, n_ctx_orig, freq_base, freq_scale,
4463        ext_factor, attn_factor, beta_fast, beta_slow, true
4464    );
4465}
4466
4467// Apparently solving `n_rot = 2pi * x * base^((2 * max_pos_emb) / n_dims)` for x, we get
4468// `corr_dim(n_rot) = n_dims * log(max_pos_emb / (n_rot * 2pi)) / (2 * log(base))`
4469static float ggml_rope_yarn_corr_dim(int n_dims, int n_ctx_orig, float n_rot, float base) {
4470    return n_dims * logf(n_ctx_orig / (n_rot * 2 * (float)M_PI)) / (2 * logf(base));
4471}
4472
4473void ggml_rope_yarn_corr_dims(
4474    int n_dims, int n_ctx_orig, float freq_base, float beta_fast, float beta_slow, float dims[2]
4475) {
4476    // start and end correction dims
4477    float start = floorf(ggml_rope_yarn_corr_dim(n_dims, n_ctx_orig, beta_fast, freq_base));
4478    float end   =  ceilf(ggml_rope_yarn_corr_dim(n_dims, n_ctx_orig, beta_slow, freq_base));
4479    dims[0] = MAX(0, start);
4480    dims[1] = MIN(n_dims - 1, end);
4481}
4482
4483// ggml_rope_back
4484
4485struct ggml_tensor * ggml_rope_ext_back(
4486        struct ggml_context * ctx,
4487        struct ggml_tensor  * a,
4488        struct ggml_tensor  * b,
4489        struct ggml_tensor  * c,
4490        int                   n_dims,
4491        int                   mode,
4492        int                   n_ctx_orig,
4493        float                 freq_base,
4494        float                 freq_scale,
4495        float                 ext_factor,
4496        float                 attn_factor,
4497        float                 beta_fast,
4498        float                 beta_slow) {
4499    struct ggml_tensor * result = ggml_rope_ext(
4500        ctx, a, b, c, n_dims, mode, n_ctx_orig, freq_base, freq_scale, ext_factor, attn_factor, beta_fast, beta_slow);
4501    result->op = GGML_OP_ROPE_BACK;
4502    return result;
4503}
4504
4505struct ggml_tensor * ggml_rope_multi_back(
4506        struct ggml_context * ctx,
4507        struct ggml_tensor  * a,
4508        struct ggml_tensor  * b,
4509        struct ggml_tensor  * c,
4510        int                   n_dims,
4511        int                   sections[4],
4512        int                   mode,
4513        int                   n_ctx_orig,
4514        float                 freq_base,
4515        float                 freq_scale,
4516        float                 ext_factor,
4517        float                 attn_factor,
4518        float                 beta_fast,
4519        float                 beta_slow) {
4520    struct ggml_tensor * result = ggml_rope_multi(
4521        ctx, a, b, c, n_dims, sections, mode, n_ctx_orig, freq_base, freq_scale, ext_factor, attn_factor, beta_fast, beta_slow);
4522    result->op = GGML_OP_ROPE_BACK;
4523    return result;
4524}
4525
4526struct ggml_tensor * ggml_rope_set_offset(
4527        struct ggml_tensor  * a,
4528        int                   n_offs) {
4529    GGML_ASSERT(a->op == GGML_OP_ROPE || a->op == GGML_OP_ROPE_BACK);
4530    GGML_ASSERT(n_offs >= 0);
4531
4532    const int32_t mode = ggml_get_op_params_i32(a, 2);
4533    GGML_ASSERT(mode != GGML_ROPE_TYPE_VISION);
4534
4535    ggml_set_op_params_i32(a, 15, n_offs);
4536    return a;
4537}
4538
4539static int64_t ggml_calc_conv_output_size(int64_t ins, int64_t ks, int s, int p, int d) {
4540    return (ins + 2 * p - d * (ks - 1) - 1) / s + 1;
4541}
4542
4543// im2col: [N, IC, IH, IW] => [N, OH, OW, IC*KH*KW]
4544// a: [OC,IC, KH, KW]
4545// b: [N, IC, IH, IW]
4546// result: [N, OH, OW, IC*KH*KW]
4547struct ggml_tensor * ggml_im2col(
4548        struct ggml_context * ctx,
4549        struct ggml_tensor  * a,
4550        struct ggml_tensor  * b,
4551        int                   s0,
4552        int                   s1,
4553        int                   p0,
4554        int                   p1,
4555        int                   d0,
4556        int                   d1,
4557        bool                  is_2D,
4558        enum ggml_type        dst_type) {
4559    if (is_2D) {
4560        GGML_ASSERT(a->ne[2] == b->ne[2]);
4561    } else {
4562        //GGML_ASSERT(b->ne[1] % a->ne[1] == 0);
4563        GGML_ASSERT(b->ne[1] == a->ne[1]);
4564        GGML_ASSERT(b->ne[3] == 1);
4565    }
4566
4567    const int64_t OH = is_2D ? ggml_calc_conv_output_size(b->ne[1], a->ne[1], s1, p1, d1) : 0;
4568    const int64_t OW =         ggml_calc_conv_output_size(b->ne[0], a->ne[0], s0, p0, d0);
4569
4570    GGML_ASSERT((!is_2D || OH > 0) && "b too small compared to a");
4571    GGML_ASSERT((OW > 0)           && "b too small compared to a");
4572
4573    const int64_t ne[4] = {
4574        is_2D ? (a->ne[2] * a->ne[1] * a->ne[0]) : a->ne[1] * a->ne[0],
4575        OW,
4576        is_2D ? OH : b->ne[2],
4577        is_2D ?      b->ne[3] : 1,
4578    };
4579
4580    struct ggml_tensor * result = ggml_new_tensor(ctx, dst_type, 4, ne);
4581    int32_t params[] = { s0, s1, p0, p1, d0, d1, (is_2D ? 1 : 0) };
4582    ggml_set_op_params(result, params, sizeof(params));
4583
4584    result->op     = GGML_OP_IM2COL;
4585    result->src[0] = a;
4586    result->src[1] = b;
4587
4588    return result;
4589}
4590
4591struct ggml_tensor * ggml_im2col_back(
4592        struct ggml_context * ctx,
4593        struct ggml_tensor  * a,
4594        struct ggml_tensor  * b,
4595        int64_t             * ne,
4596        int                   s0,
4597        int                   s1,
4598        int                   p0,
4599        int                   p1,
4600        int                   d0,
4601        int                   d1,
4602        bool                  is_2D) {
4603    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
4604    int32_t params[] = { s0, s1, p0, p1, d0, d1, (is_2D ? 1 : 0) };
4605    ggml_set_op_params(result, params, sizeof(params));
4606
4607    result->op     = GGML_OP_IM2COL_BACK;
4608    result->src[0] = a;
4609    result->src[1] = b;
4610
4611    return result;
4612}
4613
4614// ggml_conv_1d
4615
4616struct ggml_tensor * ggml_conv_1d(
4617        struct ggml_context * ctx,
4618        struct ggml_tensor  * a,
4619        struct ggml_tensor  * b,
4620        int                   s0,
4621        int                   p0,
4622        int                   d0) {
4623    struct ggml_tensor * im2col = ggml_im2col(ctx, a, b, s0, 0, p0, 0, d0, 0, false, a->type == GGML_TYPE_BF16 ? GGML_TYPE_F32 : GGML_TYPE_F16); // [N, OL, IC * K]
4624
4625    struct ggml_tensor * result =
4626        ggml_mul_mat(ctx,
4627                ggml_reshape_2d(ctx, im2col, im2col->ne[0], (im2col->ne[2] * im2col->ne[1])), // [N, OL, IC * K] => [N*OL, IC * K]
4628                ggml_reshape_2d(ctx, a, (a->ne[0] * a->ne[1]), a->ne[2]));                    // [OC,IC, K] => [OC, IC * K]
4629
4630    result = ggml_reshape_3d(ctx, result, im2col->ne[1], a->ne[2], im2col->ne[2]); // [N, OC, OL]
4631
4632    return result;
4633}
4634
4635// ggml_conv_1d_ph
4636
4637struct ggml_tensor* ggml_conv_1d_ph(
4638        struct ggml_context * ctx,
4639        struct ggml_tensor  * a,
4640        struct ggml_tensor  * b,
4641        int                   s,
4642        int                   d) {
4643    return ggml_conv_1d(ctx, a, b, s, a->ne[0] / 2, d);
4644}
4645
4646// ggml_conv_1d_dw
4647
4648struct ggml_tensor * ggml_conv_1d_dw(
4649        struct ggml_context * ctx,
4650        struct ggml_tensor  * a,
4651        struct ggml_tensor  * b,
4652        int                   s0,
4653        int                   p0,
4654        int                   d0) {
4655    struct ggml_tensor * new_b = ggml_reshape_4d(ctx, b, b->ne[0], 1, b->ne[1], b->ne[2]);
4656
4657    struct ggml_tensor * im2col = ggml_im2col(ctx, a, new_b, s0, 0, p0, 0, d0, 0, false, a->type == GGML_TYPE_BF16 ? GGML_TYPE_F32 : GGML_TYPE_F16);
4658
4659    struct ggml_tensor * result = ggml_mul_mat(ctx, im2col, a);
4660
4661    result = ggml_reshape_3d(ctx, result, result->ne[0], result->ne[2], 1);
4662
4663    return result;
4664}
4665
4666// ggml_conv_1d_dw_ph
4667
4668struct ggml_tensor * ggml_conv_1d_dw_ph(
4669        struct ggml_context * ctx,
4670        struct ggml_tensor  * a,
4671        struct ggml_tensor  * b,
4672        int                   s0,
4673        int                   d0) {
4674    return ggml_conv_1d_dw(ctx, a, b, s0, a->ne[0] / 2, d0);
4675}
4676
4677// ggml_col2im_1d
4678
4679struct ggml_tensor * ggml_col2im_1d(
4680        struct ggml_context * ctx,
4681        struct ggml_tensor  * a,
4682        int                   s0,
4683        int                   oc,
4684        int                   p0) {
4685    GGML_ASSERT(ggml_is_matrix(a));
4686    GGML_ASSERT(ggml_is_contiguous(a));
4687    GGML_ASSERT(a->type == GGML_TYPE_F32 || a->type == GGML_TYPE_F16 || a->type == GGML_TYPE_BF16);
4688    GGML_ASSERT(s0 > 0);
4689    GGML_ASSERT(oc > 0);
4690    GGML_ASSERT(p0 >= 0);
4691
4692    const int64_t K_OC = a->ne[0];
4693    const int64_t T_in = a->ne[1];
4694    const int64_t K = K_OC / oc;
4695    const int64_t T_out = (T_in - 1) * s0 + K - 2 * p0;
4696
4697    GGML_ASSERT(K_OC == K * oc);  // a->ne[0] must be a whole number of oc blocks
4698    GGML_ASSERT(K > 0 && T_out > 0);
4699
4700    const int64_t ne[4] = { T_out, oc, 1, 1 };
4701    struct ggml_tensor * result = ggml_new_tensor(ctx, a->type, 2, ne);
4702
4703    int32_t params[] = { s0, (int32_t)oc, (int32_t)p0 };
4704    ggml_set_op_params(result, params, sizeof(params));
4705
4706    result->op     = GGML_OP_COL2IM_1D;
4707    result->src[0] = a;
4708
4709    return result;
4710}
4711
4712// ggml_conv_transpose_1d
4713
4714static int64_t ggml_calc_conv_transpose_1d_output_size(int64_t ins, int64_t ks, int s, int p, int d) {
4715    return (ins - 1) * s - 2 * p + d * (ks - 1) + 1;
4716}
4717
4718GGML_API struct ggml_tensor * ggml_conv_transpose_1d(
4719        struct ggml_context * ctx,
4720        struct ggml_tensor  * a,
4721        struct ggml_tensor  * b,
4722        int                   s0,
4723        int                   p0,
4724        int                   d0) {
4725    GGML_ASSERT(ggml_is_matrix(b));
4726    GGML_ASSERT(a->ne[2] == b->ne[1]);
4727    GGML_ASSERT(a->ne[3] == 1);
4728
4729    GGML_ASSERT(p0 == 0);
4730    GGML_ASSERT(d0 == 1);
4731
4732    const int64_t ne[4] = {
4733        ggml_calc_conv_transpose_1d_output_size(b->ne[0], a->ne[0], s0, 0 /*p0*/, 1 /*d0*/),
4734        a->ne[1], b->ne[2], 1,
4735    };
4736    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
4737
4738    int32_t params[] = { s0, p0, d0 };
4739    ggml_set_op_params(result, params, sizeof(params));
4740
4741    result->op     = GGML_OP_CONV_TRANSPOSE_1D;
4742    result->src[0] = a;
4743    result->src[1] = b;
4744
4745    return result;
4746}
4747
4748// ggml_conv_2d
4749
4750// a: [OC,IC, KH, KW]
4751// b: [N, IC, IH, IW]
4752// result: [N, OC, OH, OW]
4753struct ggml_tensor * ggml_conv_2d(
4754        struct ggml_context * ctx,
4755        struct ggml_tensor  * a,
4756        struct ggml_tensor  * b,
4757        int                   s0,
4758        int                   s1,
4759        int                   p0,
4760        int                   p1,
4761        int                   d0,
4762        int                   d1) {
4763    struct ggml_tensor * im2col = ggml_im2col(ctx, a, b, s0, s1, p0, p1, d0, d1, true, a->type == GGML_TYPE_BF16 ? GGML_TYPE_F32 : GGML_TYPE_F16); // [N, OH, OW, IC * KH * KW]
4764
4765    struct ggml_tensor * result =
4766        ggml_mul_mat(ctx,
4767                ggml_reshape_2d(ctx, im2col, im2col->ne[0],  im2col->ne[3] * im2col->ne[2] * im2col->ne[1]), // [N, OH, OW, IC * KH * KW] => [N*OH*OW, IC * KH * KW]
4768                ggml_reshape_2d(ctx, a, (a->ne[0] * a->ne[1] * a->ne[2]),  a->ne[3]));                       // [OC,IC, KH, KW] => [OC, IC * KH * KW]
4769
4770    result = ggml_reshape_4d(ctx, result, im2col->ne[1], im2col->ne[2], im2col->ne[3], a->ne[3]); // [OC, N, OH, OW]
4771    result = ggml_cont(ctx, ggml_permute(ctx, result, 0, 1, 3, 2)); // [N, OC, OH, OW]
4772
4773
4774    return result;
4775}
4776
4777// a: [OC*IC, KD, KH, KW]
4778// b: [N*IC, ID, IH, IW]
4779// result: [N*OD, OH, OW, IC * KD * KH * KW]
4780struct ggml_tensor * ggml_im2col_3d(
4781        struct ggml_context * ctx,
4782        struct ggml_tensor  * a,
4783        struct ggml_tensor  * b,
4784        int64_t               IC,
4785        int                   s0, // stride width
4786        int                   s1, // stride height
4787        int                   s2, // stride depth
4788        int                   p0, // padding width
4789        int                   p1, // padding height
4790        int                   p2, // padding depth
4791        int                   d0, // dilation width
4792        int                   d1, // dilation height
4793        int                   d2, // dilation depth
4794        enum ggml_type        dst_type) {
4795    const int64_t N = b->ne[3] / IC;
4796    const int64_t ID = b->ne[2];
4797    const int64_t IH = b->ne[1];
4798    const int64_t IW = b->ne[0];
4799
4800    const int64_t OC = a->ne[3] / IC;
4801    UNUSED(OC);
4802    const int64_t KD = a->ne[2];
4803    const int64_t KH = a->ne[1];
4804    const int64_t KW = a->ne[0];
4805    const int64_t OD = ggml_calc_conv_output_size(ID, KD, s2, p2, d2);
4806    const int64_t OH = ggml_calc_conv_output_size(IH, KH, s1, p1, d1);
4807    const int64_t OW = ggml_calc_conv_output_size(IW, KW, s0, p0, d0);
4808
4809    GGML_ASSERT((OD > 0)  && "b too small compared to a");
4810    GGML_ASSERT((OH > 0)  && "b too small compared to a");
4811    GGML_ASSERT((OW > 0)  && "b too small compared to a");
4812
4813
4814    const int64_t ne[4] = {KW*KH*KD*IC, OW, OH, OD*N};
4815
4816    struct ggml_tensor * result = ggml_new_tensor(ctx, dst_type, 4, ne);
4817    int32_t params[] = { s0, s1, s2, p0, p1, p2, d0, d1, d2, (int32_t)IC};
4818    ggml_set_op_params(result, params, sizeof(params));
4819
4820    result->op     = GGML_OP_IM2COL_3D;
4821    result->src[0] = a;
4822    result->src[1] = b;
4823
4824    return result;
4825}
4826
4827// a: [OC*IC, KD, KH, KW]
4828// b: [N*IC, ID, IH, IW]
4829// result: [N*OC, OD, OH, OW]
4830struct ggml_tensor * ggml_conv_3d(
4831        struct ggml_context * ctx,
4832        struct ggml_tensor  * a,
4833        struct ggml_tensor  * b,
4834        int64_t               IC,
4835        int                   s0, // stride width
4836        int                   s1, // stride height
4837        int                   s2, // stride depth
4838        int                   p0, // padding width
4839        int                   p1, // padding height
4840        int                   p2, // padding depth
4841        int                   d0, // dilation width
4842        int                   d1, // dilation height
4843        int                   d2  // dilation depth
4844        ) {
4845    struct ggml_tensor * im2col = ggml_im2col_3d(ctx, a, b, IC, s0, s1, s2, p0, p1, p2, d0, d1, d2, a->type == GGML_TYPE_BF16 ? GGML_TYPE_F32 : GGML_TYPE_F16); // [N*OD, OH, OW, IC * KD * KH * KW]
4846
4847    int64_t OC = a->ne[3] / IC;
4848    int64_t N = b->ne[3] / IC;
4849    struct ggml_tensor * result =
4850        ggml_mul_mat(ctx,
4851                ggml_reshape_2d(ctx, im2col, im2col->ne[0], im2col->ne[3] * im2col->ne[2] * im2col->ne[1]), // [N*OD, OH, OW, IC * KD * KH * KW] => [N*OD*OH*OW, IC * KD * KH * KW]
4852                ggml_reshape_2d(ctx, a, (a->ne[0] * a->ne[1] * a->ne[2] * IC), OC));                          // [OC*IC, KD, KH, KW] => [OC, IC * KD * KH * KW]
4853
4854    int64_t OD = im2col->ne[3] / N;
4855    result = ggml_reshape_4d(ctx, result, im2col->ne[1]*im2col->ne[2], OD, N, OC); // [OC, N*OD*OH*OW] => [OC, N, OD, OH*OW]
4856    result = ggml_cont(ctx, ggml_permute(ctx, result, 0, 1, 3, 2)); // [N, OC, OD, OH*OW]
4857    result = ggml_reshape_4d(ctx, result, im2col->ne[1], im2col->ne[2], OD, OC * N); // [N*OC, OD, OH, OW]
4858
4859    return result;
4860}
4861
4862// ggml_conv_2d_sk_p0
4863
4864struct ggml_tensor * ggml_conv_2d_sk_p0(
4865        struct ggml_context * ctx,
4866        struct ggml_tensor  * a,
4867        struct ggml_tensor  * b) {
4868    return ggml_conv_2d(ctx, a, b, a->ne[0], a->ne[1], 0, 0, 1, 1);
4869}
4870
4871// ggml_conv_2d_s1_ph
4872
4873struct ggml_tensor * ggml_conv_2d_s1_ph(
4874        struct ggml_context * ctx,
4875        struct ggml_tensor  * a,
4876        struct ggml_tensor  * b) {
4877    return ggml_conv_2d(ctx, a, b, 1, 1, a->ne[0] / 2, a->ne[1] / 2, 1, 1);
4878}
4879
4880// ggml_conv_2d_dw
4881
4882struct ggml_tensor * ggml_conv_2d_dw(
4883        struct ggml_context * ctx,
4884        struct ggml_tensor  * a,
4885        struct ggml_tensor  * b,
4886        int                   s0,
4887        int                   s1,
4888        int                   p0,
4889        int                   p1,
4890        int                   d0,
4891        int                   d1) {
4892    struct ggml_tensor * new_a = ggml_reshape_4d(ctx, a, a->ne[0], a->ne[1], 1, a->ne[2] * a->ne[3]);
4893    struct ggml_tensor * im2col = ggml_im2col(ctx, new_a,
4894                                        ggml_reshape_4d(ctx, b, b->ne[0], b->ne[1], 1, b->ne[2] * b->ne[3]),
4895                                        s0, s1, p0, p1, d0, d1, true, a->type == GGML_TYPE_BF16 ? GGML_TYPE_F32 : GGML_TYPE_F16); // [N * IC, OH, OW, KH * KW]
4896    struct ggml_tensor * new_b = ggml_reshape_4d(ctx, im2col, im2col->ne[0], im2col->ne[2] * im2col->ne[1], b->ne[2], b->ne[3]); // [N * IC, OH, OW, KH * KW] => [N, IC, OH * OW, KH * KW]
4897
4898    new_a = ggml_reshape_4d(ctx, new_a, (new_a->ne[0] * new_a->ne[1]), new_a->ne[2],  new_a->ne[3], 1);                       // [OC,1, KH, KW] => [1, OC, 1, KH * KW]
4899    struct ggml_tensor * result = ggml_mul_mat(ctx, new_a, new_b);
4900    result = ggml_reshape_4d(ctx, result, im2col->ne[1], im2col->ne[2], b->ne[2], b->ne[3]); // [N, OC, OH, OW]
4901
4902    return result;
4903}
4904
4905// ggml_conv_2d_dw_direct
4906
4907struct ggml_tensor * ggml_conv_2d_dw_direct(
4908        struct ggml_context * ctx,
4909        struct ggml_tensor  * a,
4910        struct ggml_tensor  * b,
4911        int                   stride0,
4912        int                   stride1,
4913        int                   pad0,
4914        int                   pad1,
4915        int                   dilation0,
4916        int                   dilation1) {
4917    GGML_ASSERT(a->ne[2] == 1);
4918    GGML_ASSERT(a->ne[3] == b->ne[2]);
4919    int64_t ne[4];
4920    ne[0] = ggml_calc_conv_output_size(b->ne[0], a->ne[0], stride0, pad0, dilation0);
4921    ne[1] = ggml_calc_conv_output_size(b->ne[1], a->ne[1], stride1, pad1, dilation1);
4922    ne[2] = b->ne[2];
4923    ne[3] = b->ne[3];
4924
4925    struct ggml_tensor * result = ggml_new_tensor(ctx, b->type, 4, ne);
4926
4927    if (ggml_is_contiguous_channels(b)) {
4928        // Result will be permuted the same way as input (CWHN order)
4929        const int64_t type_size = ggml_type_size(result->type);
4930        GGML_ASSERT(ggml_blck_size(result->type) == 1);
4931        result->nb[0] = result->ne[2] * type_size;
4932        result->nb[1] = result->ne[0] * result->nb[0];
4933        result->nb[2] = type_size;
4934    }
4935
4936    int32_t params[] = { stride0, stride1, pad0, pad1, dilation0, dilation1 };
4937    ggml_set_op_params(result, params, sizeof(params));
4938
4939    result->op     = GGML_OP_CONV_2D_DW;
4940    result->src[0] = a;
4941    result->src[1] = b;
4942    return result;
4943}
4944
4945// ggml_conv_2d_direct
4946
4947struct ggml_tensor * ggml_conv_2d_direct(
4948        struct ggml_context * ctx,
4949        struct ggml_tensor  * a,   // convolution kernel [KW, KH, IC, OC]
4950        struct ggml_tensor  * b,   // input data [W, H, C, N]
4951        int                   s0,  // stride dimension 0
4952        int                   s1,  // stride dimension 1
4953        int                   p0,  // padding dimension 0
4954        int                   p1,  // padding dimension 1
4955        int                   d0,  // dilation dimension 0
4956        int                   d1) {// dilation dimension 1
4957
4958    GGML_ASSERT(a->ne[2] == b->ne[2]);
4959    //GGML_ASSERT(a->type == b->type);
4960
4961    int64_t ne[4];
4962    ne[0] = ggml_calc_conv_output_size(b->ne[0], a->ne[0], s0, p0, d0);
4963    ne[1] = ggml_calc_conv_output_size(b->ne[1], a->ne[1], s1, p1, d1);
4964    ne[2] = a->ne[3];
4965    ne[3] = b->ne[3];
4966
4967    struct ggml_tensor * result = ggml_new_tensor(ctx, b->type, 4, ne);
4968
4969    ggml_set_op_params_i32(result, 0, s0);
4970    ggml_set_op_params_i32(result, 1, s1);
4971    ggml_set_op_params_i32(result, 2, p0);
4972    ggml_set_op_params_i32(result, 3, p1);
4973    ggml_set_op_params_i32(result, 4, d0);
4974    ggml_set_op_params_i32(result, 5, d1);
4975
4976    result->op = GGML_OP_CONV_2D;
4977    result->src[0] = a;
4978    result->src[1] = b;
4979
4980    return result;
4981}
4982
4983// ggml_conv_3d_direct
4984
4985struct ggml_tensor * ggml_conv_3d_direct(
4986        struct ggml_context * ctx,
4987        struct ggml_tensor  * a,
4988        struct ggml_tensor  * b,
4989        int                   s0,
4990        int                   s1,
4991        int                   s2,
4992        int                   p0,
4993        int                   p1,
4994        int                   p2,
4995        int                   d0,
4996        int                   d1,
4997        int                   d2,
4998        int                   c,
4999        int                   n,
5000        int                   oc) {
5001
5002    GGML_ASSERT(a->ne[3] == (int64_t) c * oc);
5003    GGML_ASSERT(b->ne[3] == (int64_t) c * n);
5004
5005    int64_t ne[4];
5006    ne[0] = ggml_calc_conv_output_size(b->ne[0], a->ne[0], s0, p0, d0);
5007    ne[1] = ggml_calc_conv_output_size(b->ne[1], a->ne[1], s1, p1, d1);
5008    ne[2] = ggml_calc_conv_output_size(b->ne[2], a->ne[2], s2, p2, d2);
5009    ne[3] = (int64_t) oc * n;
5010
5011    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
5012
5013    ggml_set_op_params_i32(result, 0,  s0);
5014    ggml_set_op_params_i32(result, 1,  s1);
5015    ggml_set_op_params_i32(result, 2,  s2);
5016    ggml_set_op_params_i32(result, 3,  p0);
5017    ggml_set_op_params_i32(result, 4,  p1);
5018    ggml_set_op_params_i32(result, 5,  p2);
5019    ggml_set_op_params_i32(result, 6,  d0);
5020    ggml_set_op_params_i32(result, 7,  d1);
5021    ggml_set_op_params_i32(result, 8,  d2);
5022    ggml_set_op_params_i32(result, 9,  c);
5023    ggml_set_op_params_i32(result, 10, n);
5024    ggml_set_op_params_i32(result, 11, oc);
5025
5026    result->op = GGML_OP_CONV_3D;
5027    result->src[0] = a;
5028    result->src[1] = b;
5029
5030    return result;
5031}
5032
5033// ggml_conv_transpose_2d_p0
5034
5035static int64_t ggml_calc_conv_transpose_output_size(int64_t ins, int64_t ks, int s, int p) {
5036    return (ins - 1) * s - 2 * p + ks;
5037}
5038
5039struct ggml_tensor * ggml_conv_transpose_2d_p0(
5040        struct ggml_context * ctx,
5041        struct ggml_tensor  * a,
5042        struct ggml_tensor  * b,
5043        int                   stride) {
5044    GGML_ASSERT(a->ne[3] == b->ne[2]);
5045
5046    const int64_t ne[4] = {
5047        ggml_calc_conv_transpose_output_size(b->ne[0], a->ne[0], stride, 0 /*p0*/),
5048        ggml_calc_conv_transpose_output_size(b->ne[1], a->ne[1], stride, 0 /*p1*/),
5049        a->ne[2], b->ne[3],
5050    };
5051
5052    struct ggml_tensor* result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
5053
5054    ggml_set_op_params_i32(result, 0, stride);
5055
5056    result->op     = GGML_OP_CONV_TRANSPOSE_2D;
5057    result->src[0] = a;
5058    result->src[1] = b;
5059
5060    return result;
5061}
5062
5063// ggml_pool_*
5064
5065static int64_t ggml_calc_pool_output_size(int64_t ins, int ks, int s, float p) {
5066    return (ins + 2 * p - ks) / s + 1;
5067}
5068
5069// ggml_pool_1d
5070
5071struct ggml_tensor * ggml_pool_1d(
5072        struct ggml_context * ctx,
5073        struct ggml_tensor  * a,
5074        enum ggml_op_pool     op,
5075        int                   k0,
5076        int                   s0,
5077        int                   p0) {
5078    const int64_t ne[4] = {
5079        ggml_calc_pool_output_size(a->ne[0], k0, s0, p0),
5080        a->ne[1],
5081        a->ne[2],
5082        a->ne[3],
5083    };
5084    GGML_ASSERT(ne[0] > 0);
5085
5086    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
5087
5088    int32_t params[] = { op, k0, s0, p0 };
5089    ggml_set_op_params(result, params, sizeof(params));
5090
5091    result->op     = GGML_OP_POOL_1D;
5092    result->src[0] = a;
5093
5094    return result;
5095}
5096
5097// ggml_pool_2d
5098
5099struct ggml_tensor * ggml_pool_2d(
5100        struct ggml_context * ctx,
5101        struct ggml_tensor  * a,
5102        enum ggml_op_pool     op,
5103        int                   k0,
5104        int                   k1,
5105        int                   s0,
5106        int                   s1,
5107        float                 p0,
5108        float                 p1) {
5109    struct ggml_tensor * result;
5110    const int64_t ne[4] = {
5111        ggml_calc_pool_output_size(a->ne[0], k0, s0, p0),
5112        ggml_calc_pool_output_size(a->ne[1], k1, s1, p1),
5113        a->ne[2],
5114        a->ne[3],
5115    };
5116    GGML_ASSERT(ne[0] > 0);
5117    GGML_ASSERT(ne[1] > 0);
5118
5119    result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
5120
5121    int32_t params[] = { op, k0, k1, s0, s1, p0, p1 };
5122    ggml_set_op_params(result, params, sizeof(params));
5123
5124    result->op     = GGML_OP_POOL_2D;
5125    result->src[0] = a;
5126
5127    return result;
5128}
5129
5130struct ggml_tensor * ggml_pool_2d_back(
5131        struct ggml_context * ctx,
5132        struct ggml_tensor  * a,
5133        struct ggml_tensor  * af,
5134        enum ggml_op_pool     op,
5135        int                   k0,
5136        int                   k1,
5137        int                   s0,
5138        int                   s1,
5139        float                 p0,
5140        float                 p1) {
5141    struct ggml_tensor * result;
5142    result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, af->ne);
5143
5144    int32_t params[] = { op, k0, k1, s0, s1, p0, p1 };
5145    ggml_set_op_params(result, params, sizeof(params));
5146
5147    result->op     = GGML_OP_POOL_2D_BACK;
5148    result->src[0] = a;
5149    result->src[1] = af;
5150
5151    return result;
5152}
5153
5154// ggml_upscale / ggml_interpolate
5155
5156static struct ggml_tensor * ggml_interpolate_impl(
5157        struct ggml_context * ctx,
5158        struct ggml_tensor  * a,
5159        int64_t               ne0,
5160        int64_t               ne1,
5161        int64_t               ne2,
5162        int64_t               ne3,
5163        uint32_t              mode) {
5164    GGML_ASSERT((mode & 0xFF) < GGML_SCALE_MODE_COUNT);
5165    // TODO: implement antialias for modes other than bilinear
5166    GGML_ASSERT(!(mode & GGML_SCALE_FLAG_ANTIALIAS) || (mode & 0xFF) == GGML_SCALE_MODE_BILINEAR);
5167    GGML_ASSERT(a->type == GGML_TYPE_F32);
5168
5169    struct ggml_tensor * result = ggml_new_tensor_4d(ctx, a->type, ne0, ne1, ne2, ne3);
5170
5171    ggml_set_op_params_i32(result, 0, (int32_t)mode);
5172
5173    result->op     = GGML_OP_UPSCALE;
5174    result->src[0] = a;
5175
5176    return result;
5177}
5178
5179struct ggml_tensor * ggml_upscale(
5180        struct ggml_context * ctx,
5181        struct ggml_tensor  * a,
5182        int                   scale_factor,
5183        enum ggml_scale_mode  mode) {
5184    GGML_ASSERT(scale_factor > 1);
5185    return ggml_interpolate_impl(ctx, a, a->ne[0] * scale_factor, a->ne[1] * scale_factor, a->ne[2], a->ne[3], mode);
5186}
5187
5188struct ggml_tensor * ggml_upscale_ext(
5189        struct ggml_context * ctx,
5190        struct ggml_tensor  * a,
5191        int                   ne0,
5192        int                   ne1,
5193        int                   ne2,
5194        int                   ne3,
5195        enum ggml_scale_mode  mode) {
5196    return ggml_interpolate_impl(ctx, a, ne0, ne1, ne2, ne3, mode);
5197}
5198
5199struct ggml_tensor * ggml_interpolate(
5200        struct ggml_context * ctx,
5201        struct ggml_tensor  * a,
5202        int64_t               ne0,
5203        int64_t               ne1,
5204        int64_t               ne2,
5205        int64_t               ne3,
5206        uint32_t              mode) {
5207    return ggml_interpolate_impl(ctx, a, ne0, ne1, ne2, ne3, mode);
5208}
5209
5210// ggml_pad
5211
5212struct ggml_tensor * ggml_pad(
5213        struct ggml_context * ctx,
5214        struct ggml_tensor  * a,
5215        int                   p0,
5216        int                   p1,
5217        int                   p2,
5218        int                   p3) {
5219    return ggml_pad_ext(ctx, a, 0, p0, 0, p1, 0, p2, 0, p3);
5220}
5221
5222// ggml_pad_circular
5223
5224struct ggml_tensor * ggml_pad_circular(
5225        struct ggml_context * ctx,
5226        struct ggml_tensor  * a,
5227        int                   p0,
5228        int                   p1,
5229        int                   p2,
5230        int                   p3) {
5231    return ggml_pad_ext_circular(ctx, a, 0, p0, 0, p1, 0, p2, 0, p3);
5232}
5233
5234struct ggml_tensor * ggml_pad_ext(
5235            struct ggml_context * ctx,
5236            struct ggml_tensor  * a,
5237            int                  lp0,
5238            int                  rp0,
5239            int                  lp1,
5240            int                  rp1,
5241            int                  lp2,
5242            int                  rp2,
5243            int                  lp3,
5244            int                  rp3
5245            ) {
5246    struct ggml_tensor * result = ggml_new_tensor_4d(ctx, a->type,
5247            a->ne[0] + lp0 + rp0,
5248            a->ne[1] + lp1 + rp1,
5249            a->ne[2] + lp2 + rp2,
5250            a->ne[3] + lp3 + rp3);
5251
5252    ggml_set_op_params_i32(result, 0, lp0);
5253    ggml_set_op_params_i32(result, 1, rp0);
5254    ggml_set_op_params_i32(result, 2, lp1);
5255    ggml_set_op_params_i32(result, 3, rp1);
5256    ggml_set_op_params_i32(result, 4, lp2);
5257    ggml_set_op_params_i32(result, 5, rp2);
5258    ggml_set_op_params_i32(result, 6, lp3);
5259    ggml_set_op_params_i32(result, 7, rp3);
5260    ggml_set_op_params_i32(result, 8, 0); // not circular by default
5261
5262
5263    result->op     = GGML_OP_PAD;
5264    result->src[0] = a;
5265
5266    return result;
5267}
5268
5269// ggml_pad_ext_circular
5270
5271struct ggml_tensor * ggml_pad_ext_circular(
5272        struct ggml_context * ctx,
5273        struct ggml_tensor  * a,
5274        int                  lp0,
5275        int                  rp0,
5276        int                  lp1,
5277        int                  rp1,
5278        int                  lp2,
5279        int                  rp2,
5280        int                  lp3,
5281        int                  rp3
5282        ) {
5283    struct ggml_tensor * result = ggml_pad_ext(ctx, a, lp0, rp0, lp1, rp1, lp2, rp2, lp3, rp3);
5284    ggml_set_op_params_i32(result, 8, 1); // circular
5285    return result;
5286}
5287
5288// ggml_pad_reflect_1d
5289
5290struct ggml_tensor * ggml_pad_reflect_1d(
5291        struct ggml_context * ctx,
5292        struct ggml_tensor  * a,
5293        int                   p0,
5294        int                   p1) {
5295    GGML_ASSERT(p0 >= 0);
5296    GGML_ASSERT(p1 >= 0);
5297
5298    GGML_ASSERT(p0 < a->ne[0]); // padding length on each size must be less than the
5299    GGML_ASSERT(p1 < a->ne[0]); // existing length of the dimension being padded
5300
5301    GGML_ASSERT(ggml_is_contiguous(a));
5302    GGML_ASSERT(a->type == GGML_TYPE_F32);
5303
5304    struct ggml_tensor * result = ggml_new_tensor_4d(ctx, a->type,
5305            a->ne[0] + p0 + p1,
5306            a->ne[1],
5307            a->ne[2],
5308            a->ne[3]);
5309
5310    int32_t params[] = { p0, p1 };
5311    ggml_set_op_params(result, params, sizeof(params));
5312
5313    result->op     = GGML_OP_PAD_REFLECT_1D;
5314    result->src[0] = a;
5315
5316    return result;
5317}
5318
5319// ggml_roll
5320
5321struct ggml_tensor * ggml_roll(
5322        struct ggml_context * ctx,
5323        struct ggml_tensor  * a,
5324        int                   shift0,
5325        int                   shift1,
5326        int                   shift2,
5327        int                   shift3) {
5328    GGML_ASSERT(a->nb[0] == ggml_type_size(a->type));
5329    GGML_ASSERT(abs(shift0) < a->ne[0]);
5330    GGML_ASSERT(abs(shift1) < a->ne[1]);
5331    GGML_ASSERT(abs(shift2) < a->ne[2]);
5332    GGML_ASSERT(abs(shift3) < a->ne[3]);
5333
5334    struct ggml_tensor * result = ggml_dup_tensor(ctx, a);
5335
5336    ggml_set_op_params_i32(result, 0, shift0);
5337    ggml_set_op_params_i32(result, 1, shift1);
5338    ggml_set_op_params_i32(result, 2, shift2);
5339    ggml_set_op_params_i32(result, 3, shift3);
5340
5341    result->op     = GGML_OP_ROLL;
5342    result->src[0] = a;
5343
5344    return result;
5345}
5346
5347// ggml_timestep_embedding
5348
5349struct ggml_tensor * ggml_timestep_embedding(
5350        struct ggml_context * ctx,
5351        struct ggml_tensor  * timesteps,
5352        int                   dim,
5353        int                   max_period) {
5354
5355    struct ggml_tensor * result = ggml_new_tensor_2d(ctx, GGML_TYPE_F32, dim, timesteps->ne[0]);
5356
5357    ggml_set_op_params_i32(result, 0, dim);
5358    ggml_set_op_params_i32(result, 1, max_period);
5359
5360    result->op     = GGML_OP_TIMESTEP_EMBEDDING;
5361    result->src[0] = timesteps;
5362
5363    return result;
5364}
5365
5366// ggml_tri
5367
5368struct ggml_tensor * ggml_tri(
5369    struct ggml_context * ctx,
5370    struct ggml_tensor  * a,
5371    enum ggml_tri_type    type) {
5372    GGML_ASSERT(a->type == GGML_TYPE_F32);
5373
5374    GGML_ASSERT(ggml_is_contiguous(a));
5375    GGML_ASSERT(a->ne[0] == a->ne[1]);
5376
5377    struct ggml_tensor * result = ggml_dup_tensor(ctx, a);
5378
5379    ggml_set_op_params_i32(result, 0, type);
5380
5381    result->op = GGML_OP_TRI;
5382    result->src[0] = a;
5383
5384    return result;
5385}
5386
5387// ggml_fill
5388
5389static struct ggml_tensor * ggml_fill_impl(
5390    struct ggml_context * ctx,
5391    struct ggml_tensor  * a,
5392    float                 c,
5393    bool                  inplace) {
5394    GGML_ASSERT(a->type == GGML_TYPE_F32 || a->type == GGML_TYPE_F16);
5395    GGML_ASSERT(ggml_is_contiguous(a));
5396
5397    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
5398
5399    ggml_set_op_params_f32(result, 0, c);
5400
5401    result->op = GGML_OP_FILL;
5402    result->src[0] = a;
5403
5404    return result;
5405}
5406
5407struct ggml_tensor * ggml_fill(
5408    struct ggml_context * ctx,
5409    struct ggml_tensor  * a,
5410    float                 c) {
5411    return ggml_fill_impl(ctx, a, c, false);
5412}
5413
5414struct ggml_tensor * ggml_fill_inplace(
5415    struct ggml_context * ctx,
5416    struct ggml_tensor  * a,
5417    float                 c) {
5418    return ggml_fill_impl(ctx, a, c, true);
5419}
5420
5421// ggml_argsort
5422
5423struct ggml_tensor * ggml_argsort(
5424        struct ggml_context  * ctx,
5425        struct ggml_tensor   * a,
5426        enum ggml_sort_order   order) {
5427    GGML_ASSERT(a->ne[0] <= INT32_MAX);
5428
5429    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_I32, GGML_MAX_DIMS, a->ne);
5430
5431    ggml_set_op_params_i32(result, 0, (int32_t) order);
5432
5433    result->op     = GGML_OP_ARGSORT;
5434    result->src[0] = a;
5435
5436    return result;
5437}
5438
5439// ggml_argsort_top_k
5440
5441struct ggml_tensor * ggml_argsort_top_k(
5442        struct ggml_context * ctx,
5443        struct ggml_tensor  * a,
5444        int                   k) {
5445    GGML_ASSERT(a->ne[0] >= k);
5446
5447    struct ggml_tensor * result = ggml_argsort(ctx, a, GGML_SORT_ORDER_DESC);
5448
5449    result = ggml_view_4d(ctx, result,
5450                k, result->ne[1], result->ne[2], result->ne[3],
5451                   result->nb[1], result->nb[2], result->nb[3],
5452                0);
5453
5454    return result;
5455}
5456
5457// ggml_top_k
5458
5459struct ggml_tensor * ggml_top_k(
5460        struct ggml_context * ctx,
5461        struct ggml_tensor  * a,
5462        int                   k) {
5463    GGML_ASSERT(a->ne[0] >= k);
5464
5465    struct ggml_tensor * result = ggml_new_tensor_4d(ctx, GGML_TYPE_I32, k, a->ne[1], a->ne[2], a->ne[3]);
5466
5467    result->op     = GGML_OP_TOP_K;
5468    result->src[0] = a;
5469
5470    return result;
5471}
5472
5473// ggml_arange
5474
5475struct ggml_tensor * ggml_arange(
5476        struct ggml_context * ctx,
5477        float                 start,
5478        float                 stop,
5479        float                 step) {
5480    GGML_ASSERT(stop > start);
5481
5482    const int64_t steps = (int64_t) ceilf((stop - start) / step);
5483
5484    struct ggml_tensor * result = ggml_new_tensor_1d(ctx, GGML_TYPE_F32, steps);
5485
5486    ggml_set_op_params_f32(result, 0, start);
5487    ggml_set_op_params_f32(result, 1, stop);
5488    ggml_set_op_params_f32(result, 2, step);
5489
5490    result->op = GGML_OP_ARANGE;
5491
5492    return result;
5493}
5494
5495// ggml_flash_attn_ext
5496
5497struct ggml_tensor * ggml_flash_attn_ext(
5498        struct ggml_context * ctx,
5499        struct ggml_tensor  * q,
5500        struct ggml_tensor  * k,
5501        struct ggml_tensor  * v,
5502        struct ggml_tensor  * mask,
5503        float                 scale,
5504        float                 max_bias,
5505        float                 logit_softcap) {
5506    GGML_ASSERT(ggml_can_mul_mat(k, q));
5507    // TODO: check if vT can be multiplied by (k*qT)
5508
5509    GGML_ASSERT(q->ne[3] == k->ne[3]);
5510    GGML_ASSERT(q->ne[3] == v->ne[3]);
5511
5512    if (mask) {
5513        GGML_ASSERT(mask->type == GGML_TYPE_F16);
5514        GGML_ASSERT(ggml_is_contiguous(mask));
5515        //GGML_ASSERT(ggml_can_repeat_rows(mask, qk));
5516
5517        GGML_ASSERT(q->ne[2] % mask->ne[2] == 0);
5518        GGML_ASSERT(q->ne[3] % mask->ne[3] == 0);
5519    }
5520
5521    if (max_bias > 0.0f) {
5522        GGML_ASSERT(mask);
5523    }
5524
5525    // permute(0, 2, 1, 3)
5526    int64_t ne[4] = { v->ne[0], q->ne[2], q->ne[1], q->ne[3] };
5527    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
5528
5529    float params[] = { scale, max_bias, logit_softcap };
5530    ggml_set_op_params(result, params, sizeof(params));
5531
5532    result->op     = GGML_OP_FLASH_ATTN_EXT;
5533    result->src[0] = q;
5534    result->src[1] = k;
5535    result->src[2] = v;
5536    result->src[3] = mask;
5537
5538    return result;
5539}
5540
5541
5542void ggml_flash_attn_ext_set_prec(
5543        struct ggml_tensor * a,
5544        enum ggml_prec       prec) {
5545    GGML_ASSERT(a->op == GGML_OP_FLASH_ATTN_EXT);
5546
5547    const int32_t prec_i32 = (int32_t) prec;
5548
5549    ggml_set_op_params_i32(a, 3, prec_i32); // scale is on first pos, max_bias on second
5550}
5551
5552enum ggml_prec ggml_flash_attn_ext_get_prec(
5553        const struct ggml_tensor * a) {
5554    GGML_ASSERT(a->op == GGML_OP_FLASH_ATTN_EXT);
5555
5556    const int32_t prec_i32 = ggml_get_op_params_i32(a, 3);
5557
5558    return (enum ggml_prec) prec_i32;
5559}
5560
5561void ggml_flash_attn_ext_set_n_kv_max(
5562        struct ggml_tensor * a,
5563        int32_t              n_kv_max) {
5564    GGML_ASSERT(a->op == GGML_OP_FLASH_ATTN_EXT);
5565    GGML_ASSERT(n_kv_max >= 0);
5566
5567    ggml_set_op_params_i32(a, 4, n_kv_max);
5568}
5569
5570void ggml_flash_attn_ext_add_sinks(
5571        struct ggml_tensor * a,
5572        struct ggml_tensor * sinks) {
5573    if (!sinks) {
5574        a->src[4] = NULL;
5575        return;
5576    }
5577
5578    GGML_ASSERT(a->op == GGML_OP_FLASH_ATTN_EXT);
5579    GGML_ASSERT(a->src[4] == NULL);
5580    GGML_ASSERT(a->src[0]->ne[2] == sinks->ne[0]);
5581    GGML_ASSERT(sinks->type == GGML_TYPE_F32);
5582
5583    a->src[4] = sinks;
5584}
5585
5586// ggml_flash_attn_back
5587
5588struct ggml_tensor * ggml_flash_attn_back(
5589        struct ggml_context * ctx,
5590        struct ggml_tensor  * q,
5591        struct ggml_tensor  * k,
5592        struct ggml_tensor  * v,
5593        struct ggml_tensor  * d,
5594        bool                  masked) {
5595    GGML_ABORT("TODO: adapt to ggml_flash_attn_ext() changes");
5596
5597    GGML_ASSERT(ggml_can_mul_mat(k, q));
5598    // TODO: check if vT can be multiplied by (k*qT)
5599
5600    // d shape [D,N,ne2,ne3]
5601    // q shape [D,N,ne2,ne3]
5602    // k shape [D,M,kvne2,ne3]
5603    // v shape [M,D,kvne2,ne3]
5604
5605    const int64_t     D = q->ne[0];
5606    const int64_t     N = q->ne[1];
5607    const int64_t     M = k->ne[1];
5608    const int64_t   ne2 = q->ne[2];
5609    const int64_t   ne3 = q->ne[3];
5610    const int64_t kvne2 = k->ne[2];
5611
5612    GGML_ASSERT(k->ne[0] == D);
5613    GGML_ASSERT(v->ne[0] == M);
5614    GGML_ASSERT(v->ne[1] == D);
5615    GGML_ASSERT(d->ne[0] == D);
5616    GGML_ASSERT(d->ne[1] == N);
5617    GGML_ASSERT(k->ne[2] == kvne2);
5618    GGML_ASSERT(k->ne[3] == ne3);
5619    GGML_ASSERT(v->ne[2] == kvne2);
5620    GGML_ASSERT(v->ne[3] == ne3);
5621    GGML_ASSERT(d->ne[2] == ne2);
5622    GGML_ASSERT(d->ne[3] == ne3);
5623
5624    GGML_ASSERT(ne2 % kvne2 == 0);
5625
5626    // store gradients of q, k and v as continuous tensors concatenated in result.
5627    // note: v and gradv are actually transposed, i.e. v->ne[0] != D.
5628    const int64_t elem_q = ggml_nelements(q);
5629    const int64_t elem_k = ggml_nelements(k);
5630    const int64_t elem_v = ggml_nelements(v);
5631
5632    enum ggml_type result_type = GGML_TYPE_F32;
5633    GGML_ASSERT(ggml_blck_size(result_type) == 1);
5634    const size_t tsize = ggml_type_size(result_type);
5635
5636    const size_t offs_q = 0;
5637    const size_t offs_k = offs_q + GGML_PAD(elem_q * tsize, GGML_MEM_ALIGN);
5638    const size_t offs_v = offs_k + GGML_PAD(elem_k * tsize, GGML_MEM_ALIGN);
5639    const size_t end    = offs_v + GGML_PAD(elem_v * tsize, GGML_MEM_ALIGN);
5640
5641    const size_t nelements = (end + tsize - 1)/tsize;
5642
5643    struct ggml_tensor * result = ggml_new_tensor_1d(ctx, GGML_TYPE_F32, nelements);
5644
5645    int32_t masked_i = masked ? 1 : 0;
5646    ggml_set_op_params(result, &masked_i, sizeof(masked_i));
5647
5648    result->op     = GGML_OP_FLASH_ATTN_BACK;
5649    result->src[0] = q;
5650    result->src[1] = k;
5651    result->src[2] = v;
5652    result->src[3] = d;
5653
5654    return result;
5655}
5656
5657// ggml_ssm_conv
5658
5659struct ggml_tensor * ggml_ssm_conv(
5660        struct ggml_context * ctx,
5661        struct ggml_tensor  * sx,
5662        struct ggml_tensor  * c) {
5663    GGML_ASSERT(ggml_is_3d(sx));
5664    GGML_ASSERT(ggml_is_matrix(c));
5665
5666    const int64_t d_conv  = c->ne[0];
5667    const int64_t d_inner = c->ne[1];
5668    const int64_t n_t     = sx->ne[0] - d_conv + 1; // tokens per sequence
5669    const int64_t n_s     = sx->ne[2];
5670
5671    // TODO: maybe support other strides than 1?
5672    GGML_ASSERT(sx->ne[0] == d_conv - 1 + n_t);
5673    GGML_ASSERT(sx->ne[1] == d_inner);
5674    GGML_ASSERT(n_t >= 0);
5675
5676    struct ggml_tensor * result = ggml_new_tensor_3d(ctx, GGML_TYPE_F32, d_inner, n_t, n_s);
5677
5678    result->op     = GGML_OP_SSM_CONV;
5679    result->src[0] = sx;
5680    result->src[1] = c;
5681
5682    return result;
5683}
5684
5685// ggml_ssm_scan
5686
5687struct ggml_tensor * ggml_ssm_scan(
5688        struct ggml_context * ctx,
5689        struct ggml_tensor  * s,
5690        struct ggml_tensor  * x,
5691        struct ggml_tensor  * dt,
5692        struct ggml_tensor  * A,
5693        struct ggml_tensor  * B,
5694        struct ggml_tensor  * C,
5695        struct ggml_tensor  * ids,
5696        int64_t               K) {
5697    GGML_ASSERT(K >= 1);
5698    GGML_ASSERT(K <= INT32_MAX);
5699    GGML_ASSERT(ggml_is_contiguous(s));
5700    GGML_ASSERT(ggml_is_contiguous(dt));
5701    GGML_ASSERT(ggml_is_contiguous(A));
5702    GGML_ASSERT(x->nb[0] == ggml_type_size(x->type));
5703    GGML_ASSERT(B->nb[0] == ggml_type_size(B->type));
5704    GGML_ASSERT(C->nb[0] == ggml_type_size(C->type));
5705    GGML_ASSERT(x->nb[1] == x->ne[0]*x->nb[0]);
5706    GGML_ASSERT(B->nb[1] == B->ne[0]*B->nb[0]);
5707    GGML_ASSERT(C->nb[1] == C->ne[0]*C->nb[0]);
5708    GGML_ASSERT(ggml_are_same_shape(B, C));
5709    GGML_ASSERT(ids->type == GGML_TYPE_I32);
5710
5711    {
5712        const int64_t d_state      = s->ne[0];
5713        const int64_t head_dim     = x->ne[0];
5714        const int64_t n_head       = x->ne[1];
5715        const int64_t n_seq_tokens = x->ne[2];
5716        const int64_t n_seqs       = x->ne[3];
5717
5718        GGML_ASSERT(dt->ne[0] == n_head);
5719        GGML_ASSERT(dt->ne[1] == n_seq_tokens);
5720        GGML_ASSERT(dt->ne[2] == n_seqs);
5721        GGML_ASSERT(ggml_is_3d(dt));
5722        GGML_ASSERT(s->ne[1] == head_dim);
5723        GGML_ASSERT(s->ne[2] == n_head);
5724        GGML_ASSERT(B->ne[0] == d_state);
5725        GGML_ASSERT(B->ne[2] == n_seq_tokens);
5726        GGML_ASSERT(B->ne[3] == n_seqs);
5727        GGML_ASSERT(ids->ne[0] == n_seqs);
5728        GGML_ASSERT(ggml_is_vector(ids));
5729        GGML_ASSERT(A->ne[1] == n_head);
5730        GGML_ASSERT(ggml_is_matrix(A));
5731
5732        if (A->ne[0] != 1) {
5733            // Mamba-1 has more granular decay factors
5734            GGML_ASSERT(A->ne[0] == d_state);
5735            GGML_ASSERT(K == 1);
5736        }
5737    }
5738
5739    // concatenated y + ssm_states
5740    struct ggml_tensor * result = ggml_new_tensor_1d(ctx, GGML_TYPE_F32, ggml_nelements(x) + K*s->ne[0]*s->ne[1]*s->ne[2]*ids->ne[0]);
5741
5742    result->op   = GGML_OP_SSM_SCAN;
5743    result->src[0] = s;
5744    result->src[1] = x;
5745    result->src[2] = dt;
5746    result->src[3] = A;
5747    result->src[4] = B;
5748    result->src[5] = C;
5749    result->src[6] = ids;
5750
5751    ggml_set_op_params_i32(result, 0, (int32_t) K);
5752
5753    return result;
5754}
5755
5756// ggml_win_part
5757
5758struct ggml_tensor * ggml_win_part(
5759        struct ggml_context * ctx,
5760        struct ggml_tensor  * a,
5761        int                   w) {
5762    GGML_ASSERT(a->ne[3] == 1);
5763    GGML_ASSERT(a->type  == GGML_TYPE_F32);
5764
5765    // padding
5766    const int px = (w - a->ne[1]%w)%w;
5767    const int py = (w - a->ne[2]%w)%w;
5768
5769    const int npx = (px + a->ne[1])/w;
5770    const int npy = (py + a->ne[2])/w;
5771    const int np  = npx*npy;
5772
5773    const int64_t ne[4] = { a->ne[0], w, w, np, };
5774    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
5775
5776    int32_t params[] = { npx, npy, w };
5777    ggml_set_op_params(result, params, sizeof(params));
5778
5779    result->op     = GGML_OP_WIN_PART;
5780    result->src[0] = a;
5781
5782    return result;
5783}
5784
5785// ggml_win_unpart
5786
5787struct ggml_tensor * ggml_win_unpart(
5788        struct ggml_context * ctx,
5789        struct ggml_tensor  * a,
5790        int                   w0,
5791        int                   h0,
5792        int                   w) {
5793    GGML_ASSERT(a->type == GGML_TYPE_F32);
5794
5795    const int64_t ne[4] = { a->ne[0], w0, h0, 1, };
5796    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 3, ne);
5797
5798    int32_t params[] = { w };
5799    ggml_set_op_params(result, params, sizeof(params));
5800
5801    result->op     = GGML_OP_WIN_UNPART;
5802    result->src[0] = a;
5803
5804    return result;
5805}
5806
5807// ggml_get_rel_pos
5808
5809struct ggml_tensor * ggml_get_rel_pos(
5810        struct ggml_context * ctx,
5811        struct ggml_tensor  * a,
5812        int                   qh,
5813        int                   kh) {
5814    GGML_ASSERT(qh == kh);
5815    GGML_ASSERT(2*MAX(qh, kh) - 1 == a->ne[1]);
5816
5817    const int64_t ne[4] = { a->ne[0], kh, qh, 1, };
5818    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F16, 3, ne);
5819
5820    result->op     = GGML_OP_GET_REL_POS;
5821    result->src[0] = a;
5822
5823    return result;
5824}
5825
5826// ggml_add_rel_pos
5827
5828static struct ggml_tensor * ggml_add_rel_pos_impl(
5829        struct ggml_context * ctx,
5830        struct ggml_tensor  * a,
5831        struct ggml_tensor  * pw,
5832        struct ggml_tensor  * ph,
5833        bool                  inplace) {
5834    GGML_ASSERT(ggml_are_same_shape(pw, ph));
5835    GGML_ASSERT(ggml_is_contiguous(a));
5836    GGML_ASSERT(ggml_is_contiguous(pw));
5837    GGML_ASSERT(ggml_is_contiguous(ph));
5838    GGML_ASSERT(ph->type == GGML_TYPE_F32);
5839    GGML_ASSERT(pw->type == GGML_TYPE_F32);
5840    GGML_ASSERT(pw->ne[3] == a->ne[2]);
5841    GGML_ASSERT(pw->ne[0]*pw->ne[0] == a->ne[0]);
5842    GGML_ASSERT(pw->ne[1]*pw->ne[2] == a->ne[1]);
5843
5844    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
5845    ggml_set_op_params_i32(result, 0, inplace ? 1 : 0);
5846
5847    result->op     = GGML_OP_ADD_REL_POS;
5848    result->src[0] = a;
5849    result->src[1] = pw;
5850    result->src[2] = ph;
5851
5852    return result;
5853}
5854
5855struct ggml_tensor * ggml_add_rel_pos(
5856        struct ggml_context * ctx,
5857        struct ggml_tensor  * a,
5858        struct ggml_tensor  * pw,
5859        struct ggml_tensor  * ph) {
5860    return ggml_add_rel_pos_impl(ctx, a, pw, ph, false);
5861}
5862
5863struct ggml_tensor * ggml_add_rel_pos_inplace(
5864        struct ggml_context * ctx,
5865        struct ggml_tensor  * a,
5866        struct ggml_tensor  * pw,
5867        struct ggml_tensor  * ph) {
5868    return ggml_add_rel_pos_impl(ctx, a, pw, ph, true);
5869}
5870
5871// ggml_rwkv_wkv6
5872
5873struct ggml_tensor * ggml_rwkv_wkv6(
5874        struct ggml_context * ctx,
5875        struct ggml_tensor  * k,
5876        struct ggml_tensor  * v,
5877        struct ggml_tensor  * r,
5878        struct ggml_tensor  * tf,
5879        struct ggml_tensor  * td,
5880        struct ggml_tensor  * state) {
5881    GGML_ASSERT(ggml_is_contiguous(k));
5882    GGML_ASSERT(ggml_is_contiguous(v));
5883    GGML_ASSERT(ggml_is_contiguous(r));
5884    GGML_ASSERT(ggml_is_contiguous(tf));
5885    GGML_ASSERT(ggml_is_contiguous(td));
5886    GGML_ASSERT(ggml_is_contiguous(state));
5887
5888    const int64_t S = k->ne[0];
5889    const int64_t H = k->ne[1];
5890    const int64_t n_tokens = k->ne[2];
5891    const int64_t n_seqs = state->ne[1];
5892    {
5893        GGML_ASSERT(v->ne[0] == S && v->ne[1] == H && v->ne[2] == n_tokens);
5894        GGML_ASSERT(r->ne[0] == S && r->ne[1] == H && r->ne[2] == n_tokens);
5895        GGML_ASSERT(td->ne[0] == S && td->ne[1] == H && td->ne[2] == n_tokens);
5896        GGML_ASSERT(ggml_nelements(state) == S * S * H * n_seqs);
5897    }
5898
5899    // concat output and new_state
5900    const int64_t ne[4] = { S * H, n_tokens + S * n_seqs, 1, 1 };
5901    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
5902
5903    result->op     = GGML_OP_RWKV_WKV6;
5904    result->src[0] = k;
5905    result->src[1] = v;
5906    result->src[2] = r;
5907    result->src[3] = tf;
5908    result->src[4] = td;
5909    result->src[5] = state;
5910
5911    return result;
5912}
5913
5914// ggml_gated_linear_attn
5915
5916struct ggml_tensor * ggml_gated_linear_attn(
5917        struct ggml_context * ctx,
5918        struct ggml_tensor  * k,
5919        struct ggml_tensor  * v,
5920        struct ggml_tensor  * q,
5921        struct ggml_tensor  * g,
5922        struct ggml_tensor  * state,
5923        float scale) {
5924    GGML_ASSERT(ggml_is_contiguous(k));
5925    GGML_ASSERT(ggml_is_contiguous(v));
5926    GGML_ASSERT(ggml_is_contiguous(q));
5927    GGML_ASSERT(ggml_is_contiguous(g));
5928    GGML_ASSERT(ggml_is_contiguous(state));
5929
5930    const int64_t S = k->ne[0];
5931    const int64_t H = k->ne[1];
5932    const int64_t n_tokens = k->ne[2];
5933    const int64_t n_seqs = state->ne[1];
5934    {
5935        GGML_ASSERT(v->ne[0] == S && v->ne[1] == H && v->ne[2] == n_tokens);
5936        GGML_ASSERT(q->ne[0] == S && q->ne[1] == H && q->ne[2] == n_tokens);
5937        GGML_ASSERT(g->ne[0] == S && g->ne[1] == H && g->ne[2] == n_tokens);
5938        GGML_ASSERT(ggml_nelements(state) == S * S * H * n_seqs);
5939    }
5940
5941    // concat output and new_state
5942    const int64_t ne[4] = { S * H, n_tokens + S * n_seqs, 1, 1 };
5943    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
5944
5945    ggml_set_op_params_f32(result, 0, scale);
5946
5947    result->op     = GGML_OP_GATED_LINEAR_ATTN;
5948    result->src[0] = k;
5949    result->src[1] = v;
5950    result->src[2] = q;
5951    result->src[3] = g;
5952    result->src[4] = state;
5953
5954    return result;
5955}
5956
5957// ggml_rwkv_wkv7
5958
5959struct ggml_tensor * ggml_rwkv_wkv7(
5960        struct ggml_context * ctx,
5961        struct ggml_tensor  * r,
5962        struct ggml_tensor  * w,
5963        struct ggml_tensor  * k,
5964        struct ggml_tensor  * v,
5965        struct ggml_tensor  * a,
5966        struct ggml_tensor  * b,
5967        struct ggml_tensor  * state) {
5968    GGML_ASSERT(ggml_is_contiguous(r));
5969    GGML_ASSERT(ggml_is_contiguous(w));
5970    GGML_ASSERT(ggml_is_contiguous(k));
5971    GGML_ASSERT(ggml_is_contiguous(v));
5972    GGML_ASSERT(ggml_is_contiguous(a));
5973    GGML_ASSERT(ggml_is_contiguous(b));
5974    GGML_ASSERT(ggml_is_contiguous(state));
5975
5976    const int64_t S = k->ne[0];
5977    const int64_t H = k->ne[1];
5978    const int64_t n_tokens = k->ne[2];
5979    const int64_t n_seqs = state->ne[1];
5980    {
5981        GGML_ASSERT(w->ne[0] == S && w->ne[1] == H && w->ne[2] == n_tokens);
5982        GGML_ASSERT(k->ne[0] == S && k->ne[1] == H && k->ne[2] == n_tokens);
5983        GGML_ASSERT(v->ne[0] == S && v->ne[1] == H && v->ne[2] == n_tokens);
5984        GGML_ASSERT(a->ne[0] == S && a->ne[1] == H && a->ne[2] == n_tokens);
5985        GGML_ASSERT(b->ne[0] == S && b->ne[1] == H && b->ne[2] == n_tokens);
5986        GGML_ASSERT(ggml_nelements(state) == S * S * H * n_seqs);
5987    }
5988
5989    // concat output and new_state
5990    const int64_t ne[4] = { S * H, n_tokens + S * n_seqs, 1, 1 };
5991    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
5992
5993    result->op     = GGML_OP_RWKV_WKV7;
5994    result->src[0] = r;
5995    result->src[1] = w;
5996    result->src[2] = k;
5997    result->src[3] = v;
5998    result->src[4] = a;
5999    result->src[5] = b;
6000    result->src[6] = state;
6001
6002    return result;
6003}
6004
6005// ggml_unary
6006
6007static struct ggml_tensor * ggml_unary_impl(
6008        struct ggml_context * ctx,
6009        struct ggml_tensor  * a,
6010        enum ggml_unary_op    op,
6011        bool                  inplace) {
6012    GGML_ASSERT(ggml_is_contiguous_rows(a));
6013
6014    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
6015
6016    ggml_set_op_params_i32(result, 0, (int32_t) op);
6017
6018    result->op     = GGML_OP_UNARY;
6019    result->src[0] = a;
6020
6021    return result;
6022}
6023
6024struct ggml_tensor * ggml_unary(
6025        struct ggml_context * ctx,
6026        struct ggml_tensor  * a,
6027        enum ggml_unary_op    op) {
6028    return ggml_unary_impl(ctx, a, op, false);
6029}
6030
6031struct ggml_tensor * ggml_unary_inplace(
6032        struct ggml_context * ctx,
6033        struct ggml_tensor  * a,
6034        enum ggml_unary_op    op) {
6035    return ggml_unary_impl(ctx, a, op, true);
6036}
6037
6038// ggml_map_custom1
6039
6040static struct ggml_tensor * ggml_map_custom1_impl(
6041        struct ggml_context      * ctx,
6042        struct ggml_tensor       * a,
6043        const  ggml_custom1_op_t   fun,
6044        int                        n_tasks,
6045        void                     * userdata,
6046        bool                       inplace) {
6047    GGML_ASSERT(n_tasks == GGML_N_TASKS_MAX || n_tasks > 0);
6048
6049    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
6050
6051    struct ggml_map_custom1_op_params params = {
6052        /*.fun      =*/ fun,
6053        /*.n_tasks  =*/ n_tasks,
6054        /*.userdata =*/ userdata
6055    };
6056    ggml_set_op_params(result, &params, sizeof(params));
6057
6058    result->op     = GGML_OP_MAP_CUSTOM1;
6059    result->src[0] = a;
6060
6061    return result;
6062}
6063
6064struct ggml_tensor * ggml_map_custom1(
6065        struct ggml_context      * ctx,
6066        struct ggml_tensor       * a,
6067        const  ggml_custom1_op_t   fun,
6068        int                        n_tasks,
6069        void                     * userdata) {
6070    return ggml_map_custom1_impl(ctx, a, fun, n_tasks, userdata, false);
6071}
6072
6073struct ggml_tensor * ggml_map_custom1_inplace(
6074        struct ggml_context      * ctx,
6075        struct ggml_tensor       * a,
6076        const  ggml_custom1_op_t   fun,
6077        int                        n_tasks,
6078        void                     * userdata) {
6079    return ggml_map_custom1_impl(ctx, a, fun, n_tasks, userdata, true);
6080}
6081
6082// ggml_map_custom2
6083
6084static struct ggml_tensor * ggml_map_custom2_impl(
6085        struct ggml_context      * ctx,
6086        struct ggml_tensor       * a,
6087        struct ggml_tensor       * b,
6088        const  ggml_custom2_op_t   fun,
6089        int                        n_tasks,
6090        void                     * userdata,
6091        bool                       inplace) {
6092    GGML_ASSERT(n_tasks == GGML_N_TASKS_MAX || n_tasks > 0);
6093
6094    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
6095
6096    struct ggml_map_custom2_op_params params = {
6097        /*.fun      =*/ fun,
6098        /*.n_tasks  =*/ n_tasks,
6099        /*.userdata =*/ userdata
6100    };
6101    ggml_set_op_params(result, &params, sizeof(params));
6102
6103    result->op     = GGML_OP_MAP_CUSTOM2;
6104    result->src[0] = a;
6105    result->src[1] = b;
6106
6107    return result;
6108}
6109
6110struct ggml_tensor * ggml_map_custom2(
6111        struct ggml_context      * ctx,
6112        struct ggml_tensor       * a,
6113        struct ggml_tensor       * b,
6114        const  ggml_custom2_op_t   fun,
6115        int                        n_tasks,
6116        void                     * userdata) {
6117    return ggml_map_custom2_impl(ctx, a, b, fun, n_tasks, userdata, false);
6118}
6119
6120struct ggml_tensor * ggml_map_custom2_inplace(
6121        struct ggml_context      * ctx,
6122        struct ggml_tensor       * a,
6123        struct ggml_tensor       * b,
6124        const  ggml_custom2_op_t   fun,
6125        int                        n_tasks,
6126        void                     * userdata) {
6127    return ggml_map_custom2_impl(ctx, a, b, fun, n_tasks, userdata, true);
6128}
6129
6130// ggml_map_custom3
6131
6132static struct ggml_tensor * ggml_map_custom3_impl(
6133        struct ggml_context      * ctx,
6134        struct ggml_tensor       * a,
6135        struct ggml_tensor       * b,
6136        struct ggml_tensor       * c,
6137        const  ggml_custom3_op_t   fun,
6138        int                        n_tasks,
6139        void                     * userdata,
6140        bool                       inplace) {
6141    GGML_ASSERT(n_tasks == GGML_N_TASKS_MAX || n_tasks > 0);
6142
6143    struct ggml_tensor * result = inplace ? ggml_view_tensor(ctx, a) : ggml_dup_tensor(ctx, a);
6144
6145    struct ggml_map_custom3_op_params params = {
6146        /*.fun      =*/ fun,
6147        /*.n_tasks  =*/ n_tasks,
6148        /*.userdata =*/ userdata
6149    };
6150    ggml_set_op_params(result, &params, sizeof(params));
6151
6152    result->op     = GGML_OP_MAP_CUSTOM3;
6153    result->src[0] = a;
6154    result->src[1] = b;
6155    result->src[2] = c;
6156
6157    return result;
6158}
6159
6160struct ggml_tensor * ggml_map_custom3(
6161        struct ggml_context      * ctx,
6162        struct ggml_tensor       * a,
6163        struct ggml_tensor       * b,
6164        struct ggml_tensor       * c,
6165        const  ggml_custom3_op_t   fun,
6166        int                        n_tasks,
6167        void                     * userdata) {
6168    return ggml_map_custom3_impl(ctx, a, b, c, fun, n_tasks, userdata, false);
6169}
6170
6171struct ggml_tensor * ggml_map_custom3_inplace(
6172        struct ggml_context      * ctx,
6173        struct ggml_tensor       * a,
6174        struct ggml_tensor       * b,
6175        struct ggml_tensor       * c,
6176        const  ggml_custom3_op_t   fun,
6177        int                        n_tasks,
6178        void                     * userdata) {
6179    return ggml_map_custom3_impl(ctx, a, b, c, fun, n_tasks, userdata, true);
6180}
6181
6182struct ggml_tensor * ggml_custom_4d(
6183        struct ggml_context * ctx,
6184        enum ggml_type        type,
6185        int64_t               ne0,
6186        int64_t               ne1,
6187        int64_t               ne2,
6188        int64_t               ne3,
6189        struct ggml_tensor ** args,
6190        int                   n_args,
6191        ggml_custom_op_t      fun,
6192        int                   n_tasks,
6193        void                * userdata) {
6194
6195    GGML_ASSERT(n_args < GGML_MAX_SRC);
6196
6197    struct ggml_tensor * result = ggml_new_tensor_4d(ctx, type, ne0, ne1, ne2, ne3);
6198
6199    struct ggml_custom_op_params params = {
6200        /*.fun      =*/ fun,
6201        /*.n_tasks  =*/ n_tasks,
6202        /*.userdata =*/ userdata
6203    };
6204    ggml_set_op_params(result, &params, sizeof(params));
6205
6206    result->op = GGML_OP_CUSTOM;
6207    for (int i = 0; i < n_args; i++) {
6208        result->src[i] = args[i];
6209    }
6210
6211    return result;
6212}
6213
6214struct ggml_tensor * ggml_custom_inplace(
6215        struct ggml_context * ctx,
6216        struct ggml_tensor  * a,
6217        struct ggml_tensor ** args,
6218        int                   n_args,
6219        ggml_custom_op_t      fun,
6220        int                   n_tasks,
6221        void                * userdata) {
6222
6223    GGML_ASSERT(n_args < GGML_MAX_SRC - 1);
6224
6225    struct ggml_tensor * result = ggml_view_tensor(ctx, a);
6226
6227    struct ggml_custom_op_params params = {
6228        /*.fun      =*/ fun,
6229        /*.n_tasks  =*/ n_tasks,
6230        /*.userdata =*/ userdata
6231    };
6232    ggml_set_op_params(result, &params, sizeof(params));
6233
6234    result->op = GGML_OP_CUSTOM;
6235    result->src[0] = a;
6236    for (int i = 0; i < n_args; i++) {
6237        result->src[i + 1] = args[i];
6238    }
6239
6240    return result;
6241}
6242// ggml_cross_entropy_loss
6243
6244struct ggml_tensor * ggml_cross_entropy_loss(
6245        struct ggml_context * ctx,
6246        struct ggml_tensor  * a,
6247        struct ggml_tensor  * b) {
6248    GGML_ASSERT(ggml_are_same_shape(a, b));
6249
6250    struct ggml_tensor * result = ggml_new_tensor_1d(ctx, a->type, 1);
6251
6252    result->op     = GGML_OP_CROSS_ENTROPY_LOSS;
6253    result->src[0] = a;
6254    result->src[1] = b;
6255
6256    return result;
6257}
6258
6259// ggml_cross_entropy_loss_back
6260
6261struct ggml_tensor * ggml_cross_entropy_loss_back(
6262        struct ggml_context * ctx,
6263        struct ggml_tensor  * a,
6264        struct ggml_tensor  * b,
6265        struct ggml_tensor  * c) {
6266    GGML_ASSERT(ggml_is_scalar(a));
6267    GGML_ASSERT(ggml_are_same_shape(b, c));
6268
6269    struct ggml_tensor * result = ggml_dup_tensor(ctx, b);
6270
6271    result->op     = GGML_OP_CROSS_ENTROPY_LOSS_BACK;
6272    result->src[0] = a;
6273    result->src[1] = b;
6274    result->src[2] = c;
6275
6276    return result;
6277}
6278
6279// opt_step_adamw
6280
6281struct ggml_tensor * ggml_opt_step_adamw(
6282        struct ggml_context * ctx,
6283        struct ggml_tensor  * a,
6284        struct ggml_tensor  * grad,
6285        struct ggml_tensor  * m,
6286        struct ggml_tensor  * v,
6287        struct ggml_tensor  * adamw_params) {
6288    GGML_ASSERT(a->flags & GGML_TENSOR_FLAG_PARAM);
6289    GGML_ASSERT(ggml_are_same_shape(a, grad));
6290    GGML_ASSERT(ggml_are_same_shape(a, m));
6291    GGML_ASSERT(ggml_are_same_shape(a, v));
6292    GGML_ASSERT(adamw_params->type == GGML_TYPE_F32);
6293    GGML_ASSERT(ggml_nelements(adamw_params) == 7);
6294
6295    struct ggml_tensor * result = ggml_view_tensor(ctx, a);
6296
6297    result->op     = GGML_OP_OPT_STEP_ADAMW;
6298    result->src[0] = a;
6299    result->src[1] = grad;
6300    result->src[2] = m;
6301    result->src[3] = v;
6302    result->src[4] = adamw_params;
6303
6304    return result;
6305}
6306
6307// opt_step_sgd
6308
6309struct ggml_tensor * ggml_opt_step_sgd(
6310        struct ggml_context * ctx,
6311        struct ggml_tensor  * a,
6312        struct ggml_tensor  * grad,
6313        struct ggml_tensor  * params) {
6314    GGML_ASSERT(a->flags & GGML_TENSOR_FLAG_PARAM);
6315    GGML_ASSERT(ggml_are_same_shape(a, grad));
6316    GGML_ASSERT(params->type == GGML_TYPE_F32);
6317    GGML_ASSERT(ggml_nelements(params) == 2);
6318
6319    struct ggml_tensor * result = ggml_view_tensor(ctx, a);
6320
6321    result->op     = GGML_OP_OPT_STEP_SGD;
6322    result->src[0] = a;
6323    result->src[1] = grad;
6324    result->src[2] = params;
6325
6326    return result;
6327}
6328
6329// solve_tri
6330
6331struct ggml_tensor * ggml_solve_tri(
6332        struct ggml_context * ctx,
6333        struct ggml_tensor  * a,
6334        struct ggml_tensor  * b,
6335        bool                  left,
6336        bool                  lower,
6337        bool                  uni) {
6338    GGML_ASSERT(a->type == GGML_TYPE_F32);
6339    GGML_ASSERT(b->type == GGML_TYPE_F32);
6340
6341    // A must be square and lower diagonal
6342    GGML_ASSERT(a->ne[0] == a->ne[1]);
6343    // B must have same outer dimension as A
6344    GGML_ASSERT(a->ne[1] == b->ne[1]);
6345
6346    // batch dimensions must be equal
6347    GGML_ASSERT(a->ne[2] == b->ne[2]);
6348    GGML_ASSERT(a->ne[3] == b->ne[3]);
6349
6350    GGML_ASSERT(ggml_is_contiguous(a));
6351    GGML_ASSERT(ggml_is_contiguous(b));
6352
6353    GGML_ASSERT(lower && left && !uni); // TODO: support other variants
6354
6355    struct ggml_tensor * result = ggml_new_tensor_4d(ctx, GGML_TYPE_F32, b->ne[0], b->ne[1], b->ne[2], b->ne[3]);
6356
6357    result->op     = GGML_OP_SOLVE_TRI;
6358    result->src[0] = a;
6359    result->src[1] = b;
6360
6361    return result;
6362}
6363
6364// ggml_gated_delta_net
6365
6366struct ggml_tensor * ggml_gated_delta_net(
6367        struct ggml_context * ctx,
6368        struct ggml_tensor  * q,
6369        struct ggml_tensor  * k,
6370        struct ggml_tensor  * v,
6371        struct ggml_tensor  * g,
6372        struct ggml_tensor  * beta,
6373        struct ggml_tensor  * state,
6374        int64_t               K) {
6375    GGML_ASSERT(ggml_is_contiguous_rows(q));
6376    GGML_ASSERT(ggml_is_contiguous_rows(k));
6377    GGML_ASSERT(ggml_is_contiguous_rows(v));
6378    GGML_ASSERT(ggml_is_contiguous(g));
6379    GGML_ASSERT(ggml_is_contiguous(beta));
6380    GGML_ASSERT(ggml_is_contiguous(state));
6381
6382    GGML_ASSERT(q->type == GGML_TYPE_F32);
6383    GGML_ASSERT(k->type == GGML_TYPE_F32);
6384    GGML_ASSERT(v->type == GGML_TYPE_F32);
6385    GGML_ASSERT(g->type == GGML_TYPE_F32);
6386    GGML_ASSERT(beta->type == GGML_TYPE_F32);
6387    GGML_ASSERT(state->type == GGML_TYPE_F32);
6388
6389    const int64_t S_v      = v->ne[0];
6390    const int64_t H        = v->ne[1];
6391    const int64_t n_tokens = v->ne[2];
6392    const int64_t n_seqs   = v->ne[3];
6393
6394    // gate: scalar [1, H, T, B] or vector [S_v, H, T, B] (KDA)
6395    GGML_ASSERT(g->ne[0] == 1 || g->ne[0] == S_v);
6396    GGML_ASSERT(beta->ne[0] == 1);
6397
6398    // state holds the initial state s0 only: [S_v, S_v, H, n_seqs]. K (snapshot slot count) is an op param.
6399    GGML_ASSERT(state->ne[0] == S_v);
6400    GGML_ASSERT(state->ne[1] == S_v);
6401    GGML_ASSERT(state->ne[2] == H);
6402    GGML_ASSERT(state->ne[3] == n_seqs);
6403    GGML_ASSERT(K >= 1);
6404    const int64_t state_rows = K * S_v * n_seqs;
6405    const int64_t ne[4] = { S_v * H, n_tokens * n_seqs + state_rows, 1, 1 };
6406    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
6407
6408    ggml_set_op_params_i32(result, 0, (int32_t) K);
6409
6410    result->op     = GGML_OP_GATED_DELTA_NET;
6411    result->src[0] = q;
6412    result->src[1] = k;
6413    result->src[2] = v;
6414    result->src[3] = g;
6415    result->src[4] = beta;
6416    result->src[5] = state;
6417
6418    return result;
6419}
6420
6421// ggml_lightning_indexer
6422
6423struct ggml_tensor * ggml_lightning_indexer(
6424        struct ggml_context * ctx,
6425        struct ggml_tensor  * q,
6426        struct ggml_tensor  * k,
6427        struct ggml_tensor  * weights,
6428        struct ggml_tensor  * mask) {
6429
6430    GGML_ASSERT(       q->type == GGML_TYPE_F32);
6431    GGML_ASSERT( weights->type == GGML_TYPE_F32);
6432    GGML_ASSERT(    mask->type == GGML_TYPE_F16);
6433    GGML_ASSERT(      q->ne[0] == k->ne[0]);
6434    GGML_ASSERT(   mask->ne[0] == k->ne[2]);
6435    GGML_ASSERT(      q->ne[1] == weights->ne[0]);
6436    GGML_ASSERT(      k->ne[1] == 1);
6437    GGML_ASSERT(   mask->ne[1] == q->ne[2]);
6438    GGML_ASSERT(      q->ne[2] == weights->ne[1]);
6439    GGML_ASSERT(weights->ne[2] == 1);
6440    GGML_ASSERT(   mask->ne[2] == 1);
6441    GGML_ASSERT(      q->ne[3] == k->ne[3]);
6442    GGML_ASSERT(      k->ne[3] == weights->ne[3]);
6443    GGML_ASSERT(weights->ne[3] % mask->ne[3] == 0);
6444
6445    int64_t ne[4] = { k->ne[2], q->ne[2], 1, q->ne[3] };
6446    struct ggml_tensor * result = ggml_new_tensor(ctx, GGML_TYPE_F32, 4, ne);
6447
6448    result->op   = GGML_OP_LIGHTNING_INDEXER;
6449    result->src[0] = q;
6450    result->src[1] = k;
6451    result->src[2] = weights;
6452    result->src[3] = mask;
6453
6454    return result;
6455}
6456
6457// ggml_dsv4_hc_comb
6458
6459struct ggml_tensor * ggml_dsv4_hc_comb(
6460        struct ggml_context * ctx,
6461        struct ggml_tensor  * mixes,
6462        struct ggml_tensor  * scale,
6463        struct ggml_tensor  * base,
6464        float                 eps,
6465        int32_t               n_iter) {
6466    GGML_ASSERT(mixes->type == GGML_TYPE_F32);
6467    GGML_ASSERT(scale->type == GGML_TYPE_F32);
6468    GGML_ASSERT(base->type == GGML_TYPE_F32);
6469    GGML_ASSERT(n_iter > 0);
6470
6471    const int64_t hc_mix_dim = mixes->ne[0];
6472    const int64_t n_tokens   = mixes->ne[1];
6473
6474    int64_t hc = 0;
6475    for (int64_t i = 1; i*i + 2*i <= hc_mix_dim; ++i) {
6476        if ((2 + i)*i == hc_mix_dim) {
6477            hc = i;
6478            break;
6479        }
6480    }
6481
6482    GGML_ASSERT(hc > 0);
6483    GGML_ASSERT(hc == 4);
6484    GGML_ASSERT(mixes->ne[2] == 1);
6485    GGML_ASSERT(mixes->ne[3] == 1);
6486    GGML_ASSERT(scale->ne[0] >= 3);
6487    GGML_ASSERT(scale->ne[1] == 1);
6488    GGML_ASSERT(scale->ne[2] == 1);
6489    GGML_ASSERT(scale->ne[3] == 1);
6490    GGML_ASSERT(base->ne[0] == hc_mix_dim);
6491    GGML_ASSERT(base->ne[1] == 1);
6492    GGML_ASSERT(base->ne[2] == 1);
6493    GGML_ASSERT(base->ne[3] == 1);
6494
6495    struct ggml_tensor * result = ggml_new_tensor_3d(ctx, GGML_TYPE_F32, hc, hc, n_tokens);
6496
6497    ggml_set_op_params_f32(result, 0, eps);
6498    ggml_set_op_params_i32(result, 1, n_iter);
6499
6500    result->op     = GGML_OP_DSV4_HC_COMB;
6501    result->src[0] = mixes;
6502    result->src[1] = scale;
6503    result->src[2] = base;
6504
6505    return result;
6506}
6507
6508// ggml_dsv4_hc_pre
6509
6510struct ggml_tensor * ggml_dsv4_hc_pre(
6511        struct ggml_context * ctx,
6512        struct ggml_tensor  * x,
6513        struct ggml_tensor  * weights) {
6514    GGML_ASSERT(x->type == GGML_TYPE_F32);
6515    GGML_ASSERT(weights->type == GGML_TYPE_F32);
6516
6517    const int64_t n_embd   = x->ne[0];
6518    const int64_t hc       = x->ne[1];
6519    const int64_t n_tokens = x->ne[2];
6520
6521    GGML_ASSERT(hc > 0);
6522    GGML_ASSERT(x->ne[3] == 1);
6523    GGML_ASSERT(weights->ne[0] == hc);
6524    GGML_ASSERT(weights->ne[1] == n_tokens);
6525    GGML_ASSERT(weights->ne[2] == 1);
6526    GGML_ASSERT(weights->ne[3] == 1);
6527
6528    struct ggml_tensor * result = ggml_new_tensor_2d(ctx, GGML_TYPE_F32, n_embd, n_tokens);
6529
6530    result->op     = GGML_OP_DSV4_HC_PRE;
6531    result->src[0] = x;
6532    result->src[1] = weights;
6533
6534    return result;
6535}
6536
6537// ggml_dsv4_hc_post
6538
6539struct ggml_tensor * ggml_dsv4_hc_post(
6540        struct ggml_context * ctx,
6541        struct ggml_tensor  * x,
6542        struct ggml_tensor  * residual,
6543        struct ggml_tensor  * post,
6544        struct ggml_tensor  * comb) {
6545    GGML_ASSERT(x->type == GGML_TYPE_F32);
6546    GGML_ASSERT(residual->type == GGML_TYPE_F32);
6547    GGML_ASSERT(post->type == GGML_TYPE_F32);
6548    GGML_ASSERT(comb->type == GGML_TYPE_F32);
6549
6550    const int64_t n_embd   = x->ne[0];
6551    const int64_t n_tokens = x->ne[1];
6552    const int64_t hc       = residual->ne[1];
6553
6554    GGML_ASSERT(hc > 0);
6555    GGML_ASSERT(x->ne[2] == 1);
6556    GGML_ASSERT(x->ne[3] == 1);
6557
6558    GGML_ASSERT(residual->ne[0] == n_embd);
6559    GGML_ASSERT(residual->ne[2] == n_tokens);
6560    GGML_ASSERT(residual->ne[3] == 1);
6561
6562    GGML_ASSERT(post->ne[0] == hc);
6563    GGML_ASSERT(post->ne[1] == n_tokens);
6564    GGML_ASSERT(post->ne[2] == 1);
6565    GGML_ASSERT(post->ne[3] == 1);
6566
6567    GGML_ASSERT(comb->ne[0] == hc);
6568    GGML_ASSERT(comb->ne[1] == hc);
6569    GGML_ASSERT(comb->ne[2] == n_tokens);
6570    GGML_ASSERT(comb->ne[3] == 1);
6571
6572    struct ggml_tensor * result = ggml_new_tensor_3d(ctx, GGML_TYPE_F32, n_embd, hc, n_tokens);
6573
6574    result->op     = GGML_OP_DSV4_HC_POST;
6575    result->src[0] = x;
6576    result->src[1] = residual;
6577    result->src[2] = post;
6578    result->src[3] = comb;
6579
6580    return result;
6581}
6582
6583////////////////////////////////////////////////////////////////////////////////
6584
6585struct ggml_hash_set ggml_hash_set_new(size_t size) {
6586    size = ggml_hash_size(size);
6587    struct ggml_hash_set result;
6588    result.size = size;
6589    result.keys = GGML_MALLOC(sizeof(struct ggml_tensor *) * size);
6590    result.used = GGML_CALLOC(ggml_bitset_size(size), sizeof(ggml_bitset_t));
6591    return result;
6592}
6593
6594void ggml_hash_set_reset(struct ggml_hash_set * hash_set) {
6595    memset(hash_set->used, 0, sizeof(ggml_bitset_t) * ggml_bitset_size(hash_set->size));
6596}
6597
6598void ggml_hash_set_free(struct ggml_hash_set * hash_set) {
6599    GGML_FREE(hash_set->used);
6600    GGML_FREE(hash_set->keys);
6601}
6602
6603size_t ggml_hash_size(size_t min_sz) {
6604    // next primes after powers of two
6605    static const size_t primes[] = {
6606        2, 3, 5, 11, 17, 37, 67, 131, 257, 521, 1031,
6607        2053, 4099, 8209, 16411, 32771, 65537, 131101,
6608        262147, 524309, 1048583, 2097169, 4194319, 8388617,
6609        16777259, 33554467, 67108879, 134217757, 268435459,
6610        536870923, 1073741827, 2147483659
6611    };
6612    static const size_t n_primes = sizeof(primes)/sizeof(primes[0]);
6613
6614    // find the smallest prime that is larger or equal than min_sz
6615    size_t l = 0;
6616    size_t r = n_primes;
6617    while (l < r) {
6618        size_t m = (l + r)/2;
6619        if (primes[m] < min_sz) {
6620            l = m + 1;
6621        } else {
6622            r = m;
6623        }
6624    }
6625    size_t sz = l < n_primes ? primes[l] : min_sz | 1;
6626    return sz;
6627}
6628
6629struct hash_map {
6630    struct ggml_hash_set set;
6631    struct ggml_tensor ** vals;
6632};
6633
6634static struct hash_map * ggml_new_hash_map(size_t size) {
6635    struct hash_map * result = GGML_MALLOC(sizeof(struct hash_map));
6636    result->set = ggml_hash_set_new(size);
6637    result->vals = GGML_CALLOC(result->set.size, sizeof(struct ggml_tensor *));
6638    return result;
6639}
6640
6641static void ggml_hash_map_free(struct hash_map * map) {
6642    ggml_hash_set_free(&map->set);
6643    GGML_FREE(map->vals);
6644    GGML_FREE(map);
6645}
6646
6647// utility functions to change gradients
6648// isrc is the index of tensor in cgraph->visited_has_set.keys
6649// the corresponding gradient (accumulators) are also at position isrc
6650// if tensor has a gradient accumulator, modify that accumulator in-place
6651// else if there is no gradient for tensor, set the corresponding value
6652// else, just add/subtract/etc. the gradients
6653
6654static void ggml_add_or_set(
6655        struct ggml_context * ctx,
6656        struct ggml_cgraph  * cgraph,
6657        size_t                isrc,
6658        struct ggml_tensor  * tensor) {
6659    struct ggml_tensor * src = cgraph->visited_hash_set.keys[isrc];
6660    GGML_ASSERT(src);
6661    if (cgraph->grads[isrc]) {
6662        cgraph->grads[isrc] = ggml_add_impl(ctx, cgraph->grads[isrc], tensor, /*inplace =*/ cgraph->grad_accs[isrc]);
6663    } else {
6664        cgraph->grads[isrc] = tensor;
6665    }
6666    ggml_format_name(cgraph->grads[isrc], "grad for %s", src->name);
6667    ggml_build_forward_expand(cgraph, cgraph->grads[isrc]);
6668}
6669
6670static void ggml_acc_or_set(
6671        struct ggml_context * ctx,
6672        struct ggml_cgraph  * cgraph,
6673        size_t                isrc,
6674        struct ggml_tensor  * tensor,
6675        const  size_t         nb1,
6676        const  size_t         nb2,
6677        const  size_t         nb3,
6678        const  size_t         offset) {
6679    struct ggml_tensor * src = cgraph->visited_hash_set.keys[isrc];
6680    GGML_ASSERT(src);
6681    if (cgraph->grads[isrc]) {
6682        cgraph->grads[isrc] = ggml_acc_impl(ctx, cgraph->grads[isrc], tensor, nb1, nb2, nb3, offset, cgraph->grad_accs[isrc]);
6683    } else {
6684        struct ggml_tensor * a_zero = ggml_scale(ctx, src, 0.0f); // FIXME this is going to produce NaN if a contains inf/NaN
6685        cgraph->grads[isrc] = ggml_acc_impl(ctx, a_zero, tensor, nb1, nb2, nb3, offset, false);
6686    }
6687    ggml_format_name(cgraph->grads[isrc], "grad for %s", cgraph->visited_hash_set.keys[isrc]->name);
6688    ggml_build_forward_expand(cgraph, cgraph->grads[isrc]);
6689}
6690
6691static void ggml_add1_or_set(
6692        struct ggml_context * ctx,
6693        struct ggml_cgraph  * cgraph,
6694        size_t                isrc,
6695        struct ggml_tensor  * tensor) {
6696    struct ggml_tensor * src = cgraph->visited_hash_set.keys[isrc];
6697    GGML_ASSERT(src);
6698    if (cgraph->grads[isrc]) {
6699        cgraph->grads[isrc] = ggml_add1_impl(ctx, cgraph->grads[isrc], tensor, cgraph->grad_accs[isrc]);
6700    } else {
6701        cgraph->grads[isrc] = ggml_repeat(ctx, tensor, src);
6702    }
6703    ggml_format_name(cgraph->grads[isrc], "grad for %s", src->name);
6704    ggml_build_forward_expand(cgraph, cgraph->grads[isrc]);
6705}
6706
6707static void ggml_sub_or_set(
6708        struct ggml_context * ctx,
6709        struct ggml_cgraph  * cgraph,
6710        size_t                isrc,
6711        struct ggml_tensor  * tensor) {
6712    struct ggml_tensor * src = cgraph->visited_hash_set.keys[isrc];
6713    GGML_ASSERT(src);
6714    if (cgraph->grads[isrc]) {
6715        cgraph->grads[isrc] = ggml_sub_impl(ctx, cgraph->grads[isrc], tensor, cgraph->grad_accs[isrc]);
6716    } else {
6717        cgraph->grads[isrc] = ggml_neg(ctx, tensor);
6718    }
6719    ggml_format_name(cgraph->grads[isrc], "grad for %s", src->name);
6720    ggml_build_forward_expand(cgraph, cgraph->grads[isrc]);
6721}
6722
6723static void ggml_compute_backward(
6724        struct ggml_context * ctx, struct ggml_cgraph * cgraph, int i, const bool * grads_needed) {
6725    struct ggml_tensor * tensor = cgraph->nodes[i];
6726    struct ggml_tensor * grad   = ggml_graph_get_grad(cgraph, tensor);
6727
6728    if (!grad) {
6729        return;
6730    }
6731
6732    struct ggml_tensor * src0 = tensor->src[0];
6733    struct ggml_tensor * src1 = tensor->src[1];
6734    struct ggml_tensor * src2 = tensor->src[2];
6735    struct ggml_hash_set * hash_set = &cgraph->visited_hash_set;
6736    const size_t isrc0 = src0 ? ggml_hash_find(hash_set, src0) : (size_t) -1;
6737    const size_t isrc1 = src1 ? ggml_hash_find(hash_set, src1) : (size_t) -1;
6738    const size_t isrc2 = src2 ? ggml_hash_find(hash_set, src2) : (size_t) -1;
6739    const bool src0_needs_grads = src0 && isrc0 != GGML_HASHSET_FULL && ggml_bitset_get(hash_set->used, isrc0) && grads_needed[isrc0];
6740    const bool src1_needs_grads = src1 && isrc1 != GGML_HASHSET_FULL && ggml_bitset_get(hash_set->used, isrc1) && grads_needed[isrc1];
6741    const bool src2_needs_grads = src2 && isrc2 != GGML_HASHSET_FULL && ggml_bitset_get(hash_set->used, isrc2) && grads_needed[isrc2];
6742
6743    switch (tensor->op) {
6744        case GGML_OP_DUP: {
6745            if (src0_needs_grads) {
6746                ggml_add_or_set(ctx, cgraph, isrc0, grad);
6747            }
6748        } break;
6749        case GGML_OP_ADD: {
6750            if (src0_needs_grads) {
6751                ggml_add_or_set(ctx, cgraph, isrc0, grad);
6752            }
6753            if (src1_needs_grads) {
6754                struct ggml_tensor * tmp = grad;
6755                if (!ggml_are_same_shape(src0, src1)) {
6756                    tmp = ggml_repeat_back(ctx, tmp, src1);
6757                }
6758                ggml_add_or_set(ctx, cgraph, isrc1, tmp);
6759            }
6760        } break;
6761        case GGML_OP_ADD1: {
6762            if (src0_needs_grads) {
6763                ggml_add_or_set(ctx, cgraph, isrc0, grad);
6764            }
6765            if (src1_needs_grads) {
6766                ggml_add_or_set(ctx, cgraph, isrc1, ggml_mean(ctx, grad)); // TODO: should probably be sum instead of mean
6767            }
6768        } break;
6769        case GGML_OP_ACC: {
6770            if (src0_needs_grads) {
6771                ggml_add_or_set(ctx, cgraph, isrc0, grad);
6772            }
6773            if (src1_needs_grads) {
6774                const size_t nb1    = ((int32_t *) tensor->op_params)[0];
6775                const size_t nb2    = ((int32_t *) tensor->op_params)[1];
6776                const size_t nb3    = ((int32_t *) tensor->op_params)[2];
6777                const size_t offset = ((int32_t *) tensor->op_params)[3];
6778
6779                struct ggml_tensor * tensor_grad_view = ggml_view_4d(ctx,
6780                    grad, src1->ne[0], src1->ne[1], src1->ne[2], src1->ne[3],
6781                    nb1, nb2, nb3, offset);
6782
6783                ggml_add_or_set(ctx, cgraph, isrc1, ggml_reshape(ctx, ggml_cont(ctx, tensor_grad_view), src1));
6784            }
6785        } break;
6786        case GGML_OP_SUB: {
6787            if (src0_needs_grads) {
6788                ggml_add_or_set(ctx, cgraph, isrc0, grad);
6789            }
6790            if (src1_needs_grads) {
6791                ggml_sub_or_set(ctx, cgraph, isrc1, grad);
6792            }
6793        } break;
6794        case GGML_OP_MUL: {
6795            if (src0_needs_grads) {
6796                ggml_add_or_set(ctx, cgraph, isrc0, ggml_mul(ctx, grad, src1));
6797            }
6798            if (src1_needs_grads) {
6799                struct ggml_tensor * tmp = ggml_mul(ctx, src0, grad);
6800                if (!ggml_are_same_shape(src0, src1)) {
6801                    tmp = ggml_repeat_back(ctx, tmp, src1);
6802                }
6803                ggml_add_or_set(ctx, cgraph, isrc1, tmp);
6804            }
6805        } break;
6806        case GGML_OP_DIV: {
6807            if (src0_needs_grads) {
6808                ggml_add_or_set(ctx, cgraph, isrc0, ggml_div(ctx, grad, src1));
6809            }
6810            if (src1_needs_grads) {
6811                ggml_sub_or_set(ctx, cgraph, isrc1, ggml_mul(ctx, grad, ggml_div(ctx, tensor, src1)));
6812            }
6813        } break;
6814        case GGML_OP_SQR: {
6815            if (src0_needs_grads) {
6816                ggml_add_or_set(ctx, cgraph, isrc0, ggml_scale(ctx, ggml_mul(ctx, src0, grad), 2.0f));
6817            }
6818        } break;
6819        case GGML_OP_SQRT: {
6820            if (src0_needs_grads) {
6821                ggml_add_or_set(ctx, cgraph, isrc0, ggml_scale(ctx, ggml_div(ctx, grad, tensor), 0.5f));
6822            }
6823        } break;
6824        case GGML_OP_LOG: {
6825            if (src0_needs_grads) {
6826                ggml_add_or_set(ctx, cgraph, isrc0, ggml_div(ctx, grad, src0));
6827            }
6828        } break;
6829        case GGML_OP_SIN: {
6830            if (src0_needs_grads) {
6831                ggml_add_or_set(ctx, cgraph, isrc0, ggml_mul(ctx, grad, ggml_cos(ctx, src0)));
6832            }
6833        } break;
6834        case GGML_OP_COS: {
6835            if (src0_needs_grads) {
6836                ggml_sub_or_set(ctx, cgraph, isrc0, ggml_mul(ctx, grad, ggml_sin(ctx, src0)));
6837            }
6838        } break;
6839        case GGML_OP_SUM: {
6840            if (src0_needs_grads) {
6841                ggml_add1_or_set(ctx, cgraph, isrc0, grad);
6842            }
6843        } break;
6844        case GGML_OP_SUM_ROWS: {
6845            if (src0_needs_grads) {
6846                ggml_add_or_set(ctx, cgraph, isrc0, ggml_repeat(ctx, grad, src0));
6847            }
6848        } break;
6849        case GGML_OP_MEAN: {
6850            if (src0_needs_grads) {
6851                ggml_add1_or_set(ctx, cgraph, isrc0, ggml_scale_impl(ctx, grad, 1.0f/src0->ne[0], 0.0, false));
6852            }
6853        } break;
6854        case GGML_OP_REPEAT: {
6855            if (src0_needs_grads) {
6856                ggml_add_or_set(ctx, cgraph, isrc0, ggml_repeat_back(ctx, grad, src0));
6857            }
6858        } break;
6859        case GGML_OP_REPEAT_BACK: {
6860            if (src0_needs_grads) {
6861                ggml_add_or_set(ctx, cgraph, isrc0, ggml_repeat(ctx, grad, src0));
6862            }
6863        } break;
6864        case GGML_OP_RMS_NORM: {
6865            if (src0_needs_grads) {
6866                float eps;
6867                memcpy(&eps, tensor->op_params, sizeof(float));
6868                ggml_add_or_set(ctx, cgraph, isrc0, ggml_rms_norm_back(ctx, grad, src0, eps));
6869            }
6870        } break;
6871        case GGML_OP_MUL_MAT: {
6872            // https://cs231n.github.io/optimization-2/#staged
6873            // # forward pass
6874            // s0 = np.random.randn(5, 10)
6875            // s1 = np.random.randn(10, 3)
6876            // t = s0.dot(s1)
6877
6878            // # now suppose we had the gradient on t from above in the circuit
6879            // dt = np.random.randn(*t.shape) # same shape as t
6880            // ds0 = dt.dot(s1.T) #.T gives the transpose of the matrix
6881            // ds1 = t.T.dot(dt)
6882
6883            // tensor.shape [m,p,qq,rr]
6884            // src0.shape   [n,m,q1,r1]
6885            // src1.shape   [n,p,qq,rr]
6886
6887            if (src0_needs_grads) {
6888                GGML_ASSERT(grad->ne[2] == src1->ne[2]);
6889                GGML_ASSERT(grad->ne[3] == src1->ne[3]);
6890                struct ggml_tensor * tmp =
6891                    ggml_out_prod(ctx, // [n,m,qq,rr]
6892                        src1,          // [n,p,qq,rr]
6893                        grad);         // [m,p,qq,rr]
6894                if (!ggml_are_same_shape(tmp, src0)) {
6895                    GGML_ASSERT(tmp->ne[0] == src0->ne[0]);
6896                    GGML_ASSERT(tmp->ne[1] == src0->ne[1]);
6897                    GGML_ASSERT(tmp->ne[3] == 1);
6898
6899                    const int64_t nr2 = tmp->ne[2] / src0->ne[2];
6900                    const size_t nb2 = tmp->nb[2] * nr2;
6901                    const size_t nb3 = tmp->nb[2];
6902
6903                    tmp = ggml_view_4d(ctx, tmp, src0->ne[0], src0->ne[1], src0->ne[2], nr2, tmp->nb[1], nb2, nb3, 0);
6904                    tmp = ggml_repeat_back(ctx, tmp, src0);
6905                }
6906                ggml_add_or_set(ctx, cgraph, isrc0, tmp);
6907            }
6908            if (src1_needs_grads) {
6909                ggml_add_or_set(ctx, cgraph, isrc1,
6910                        // ggml_mul_mat(ctx,                   // [n,p,qq,rr]
6911                        //     ggml_cont(ctx,                  // [m,n,q1,r1]
6912                        //         ggml_transpose(ctx, src0)), // [m,n,q1,r1]
6913                        //     grad),                          // [m,p,qq,rr]
6914
6915                        // when src0 is bigger than tensor->grad (this is mostly the case in llama),
6916                        // avoid transpose of src0, rather transpose smaller tensor->grad
6917                        // and then use ggml_out_prod
6918                        ggml_out_prod(ctx,      // [n,p,qq,rr]
6919                            src0,               // [n,m,q1,r1]
6920                            ggml_transpose(ctx, // [p,m,qq,rr]
6921                                grad)));        // [m,p,qq,rr]
6922            }
6923        } break;
6924        case GGML_OP_SCALE: {
6925            if (src0_needs_grads) {
6926                float s;
6927                memcpy(&s, tensor->op_params, sizeof(float));
6928                ggml_add_or_set(ctx, cgraph, isrc0, ggml_scale_impl(ctx, grad, s, 0.0, false));
6929            }
6930        } break;
6931        case GGML_OP_SET: {
6932            const size_t nb1    = ((const int32_t *) tensor->op_params)[0];
6933            const size_t nb2    = ((const int32_t *) tensor->op_params)[1];
6934            const size_t nb3    = ((const int32_t *) tensor->op_params)[2];
6935            const size_t offset = ((const int32_t *) tensor->op_params)[3];
6936
6937            struct ggml_tensor * tensor_grad_view = NULL;
6938
6939            if (src0_needs_grads || src1_needs_grads) {
6940                GGML_ASSERT(src0->type == tensor->type);
6941                GGML_ASSERT(!cgraph->grads[isrc0] ||                      cgraph->grads[isrc0]->type == grad->type);
6942                GGML_ASSERT(!cgraph->grads[isrc1] || !src1_needs_grads || cgraph->grads[isrc1]->type == grad->type);
6943
6944                tensor_grad_view = ggml_view_4d(ctx,
6945                    grad, src1->ne[0], src1->ne[1], src1->ne[2], src1->ne[3],
6946                    nb1, nb2, nb3, offset);
6947            }
6948
6949            if (src0_needs_grads) {
6950                struct ggml_tensor * tmp = ggml_neg(ctx, tensor_grad_view);
6951                ggml_add_or_set(ctx, cgraph, isrc0, ggml_acc_impl(ctx, grad, tmp, nb1, nb2, nb3, offset, false));
6952            }
6953
6954            if (src1_needs_grads) {
6955                ggml_add_or_set(ctx, cgraph, isrc1, ggml_reshape(ctx, ggml_cont(ctx, tensor_grad_view), src1));
6956            }
6957        } break;
6958        case GGML_OP_CPY: {
6959            // cpy overwrites value of src1 by src0 and returns view(src1)
6960            // the overwriting is mathematically equivalent to:
6961            // tensor = src0 * 1 + src1 * 0
6962            if (src0_needs_grads) {
6963                // dsrc0 = dtensor * 1
6964                ggml_add_or_set(ctx, cgraph, isrc0, ggml_reshape(ctx, grad, src0));
6965            }
6966            if (src1_needs_grads) {
6967                // dsrc1 = dtensor * 0 -> noop
6968            }
6969        } break;
6970        case GGML_OP_CONT: {
6971            // same as cpy
6972            if (src0_needs_grads) {
6973                GGML_ASSERT(!cgraph->grads[isrc0] || ggml_is_contiguous(cgraph->grads[isrc0]));
6974                GGML_ASSERT(ggml_is_contiguous(grad));
6975                GGML_ASSERT(ggml_nelements(tensor) == ggml_nelements(src0));
6976                ggml_add_or_set(ctx, cgraph, isrc0,
6977                    ggml_are_same_shape(tensor, src0) ? grad : ggml_reshape(ctx, grad, src0));
6978            }
6979        } break;
6980        case GGML_OP_RESHAPE: {
6981            if (src0_needs_grads) {
6982                struct ggml_tensor * grad_cont = ggml_is_contiguous(grad) ? grad : ggml_cont(ctx, grad);
6983                ggml_add_or_set(ctx, cgraph, isrc0, ggml_reshape(ctx, grad_cont, src0));
6984            }
6985        } break;
6986        case GGML_OP_VIEW: {
6987            if (src0_needs_grads) {
6988                size_t offset;
6989
6990                memcpy(&offset, tensor->op_params, sizeof(offset));
6991
6992                size_t nb1 = tensor->nb[1];
6993                size_t nb2 = tensor->nb[2];
6994                size_t nb3 = tensor->nb[3];
6995
6996                if (cgraph->grads[isrc0] && src0->type != cgraph->grads[isrc0]->type) {
6997                    // gradient is typically F32, but src0 could be other type
6998                    size_t ng = ggml_element_size(cgraph->grads[isrc0]);
6999                    size_t n0 = ggml_element_size(src0);
7000                    GGML_ASSERT(offset % n0 == 0);
7001                    GGML_ASSERT(nb1 % n0 == 0);
7002                    GGML_ASSERT(nb2 % n0 == 0);
7003                    GGML_ASSERT(nb3 % n0 == 0);
7004                    offset = (offset / n0) * ng;
7005                    nb1 = (nb1 / n0) * ng;
7006                    nb2 = (nb2 / n0) * ng;
7007                    nb3 = (nb3 / n0) * ng;
7008                }
7009
7010                ggml_acc_or_set(ctx, cgraph, isrc0, grad, nb1, nb2, nb3, offset);
7011            }
7012        } break;
7013        case GGML_OP_PERMUTE: {
7014            if (src0_needs_grads) {
7015                const int32_t * axes = (const int32_t *) tensor->op_params;
7016                const int axis0 = axes[0] & 0x3;
7017                const int axis1 = axes[1] & 0x3;
7018                const int axis2 = axes[2] & 0x3;
7019                const int axis3 = axes[3] & 0x3;
7020                int axb[4] = {0,0,0,0}; // axes backward
7021                axb[axis0] = 0;
7022                axb[axis1] = 1;
7023                axb[axis2] = 2;
7024                axb[axis3] = 3;
7025                ggml_add_or_set(ctx, cgraph, isrc0, ggml_permute(ctx, grad, axb[0], axb[1], axb[2], axb[3]));
7026            }
7027        } break;
7028        case GGML_OP_TRANSPOSE: {
7029            if (src0_needs_grads) {
7030                ggml_add_or_set(ctx, cgraph, isrc0, ggml_transpose(ctx, grad));
7031            }
7032        } break;
7033        case GGML_OP_GET_ROWS: {
7034            if (src0_needs_grads) {
7035                ggml_add_or_set(ctx, cgraph, isrc0, ggml_get_rows_back(ctx, grad, src1, src0));
7036            }
7037            if (src1_needs_grads) {
7038                // noop
7039            }
7040        } break;
7041        case GGML_OP_DIAG_MASK_INF: {
7042            if (src0_needs_grads) {
7043                /* ggml_diag_mask_inf_impl() shouldn't be here */
7044                /* ref:  https://github.com/ggml-org/llama.cpp/pull/4203#discussion_r1412377992 */
7045                const int n_past = ((const int32_t *) tensor->op_params)[0];
7046                ggml_add_or_set(ctx, cgraph, isrc0, ggml_diag_mask_zero_impl(ctx, grad, n_past, false));
7047            }
7048        } break;
7049        case GGML_OP_DIAG_MASK_ZERO: {
7050            if (src0_needs_grads) {
7051                const int n_past = ((const int32_t *) tensor->op_params)[0];
7052                ggml_add_or_set(ctx, cgraph, isrc0, ggml_diag_mask_zero_impl(ctx, grad, n_past, false));
7053            }
7054        } break;
7055        case GGML_OP_SOFT_MAX: {
7056            if (src0_needs_grads) {
7057                float scale    = 1.0f;
7058                float max_bias = 0.0f;
7059
7060                memcpy(&scale,    (const float *) tensor->op_params + 0, sizeof(float));
7061                memcpy(&max_bias, (const float *) tensor->op_params + 1, sizeof(float));
7062
7063                ggml_add_or_set(ctx, cgraph, isrc0, ggml_soft_max_ext_back(ctx, grad, tensor, scale, max_bias));
7064            }
7065            GGML_ASSERT((!src1 || !src1_needs_grads) && "backward pass for softmax mask not implemented");
7066        } break;
7067        case GGML_OP_ROPE: {
7068            if (src0_needs_grads) {
7069                //const int n_past = ((int32_t *) tensor->op_params)[0];
7070                const int n_dims     = ((const int32_t *) tensor->op_params)[1];
7071                const int mode       = ((const int32_t *) tensor->op_params)[2];
7072                //const int n_ctx      = ((int32_t *) tensor->op_params)[3];
7073                const int n_ctx_orig = ((const int32_t *) tensor->op_params)[4];
7074                float freq_base, freq_scale, ext_factor, attn_factor, beta_fast, beta_slow;
7075                int sections[4] = {0, 0, 0, 0};
7076
7077                memcpy(&freq_base,   (const float *) tensor->op_params +  5, sizeof(float));
7078                memcpy(&freq_scale,  (const float *) tensor->op_params +  6, sizeof(float));
7079                memcpy(&ext_factor,  (const float *) tensor->op_params +  7, sizeof(float));
7080                memcpy(&attn_factor, (const float *) tensor->op_params +  8, sizeof(float));
7081                memcpy(&beta_fast,   (const float *) tensor->op_params +  9, sizeof(float));
7082                memcpy(&beta_slow,   (const float *) tensor->op_params + 10, sizeof(float));
7083                memcpy(&sections,                    tensor->op_params + 11, sizeof(sections));
7084
7085                struct ggml_tensor * rope_back = grad->ne[2] == src1->ne[0] ?
7086                    ggml_rope_ext_back(ctx, grad, src1, src2, n_dims,
7087                        mode, n_ctx_orig, freq_base, freq_scale, ext_factor, attn_factor, beta_fast, beta_slow) :
7088                    ggml_rope_multi_back(ctx, grad, src1, src2, n_dims, sections,
7089                        mode, n_ctx_orig, freq_base, freq_scale, ext_factor, attn_factor, beta_fast, beta_slow);
7090                ggml_add_or_set(ctx, cgraph, isrc0, rope_back);
7091            }
7092            GGML_ASSERT((!src2 || !src2_needs_grads) && "gradients for freq factors not implemented");
7093        } break;
7094        case GGML_OP_IM2COL: {
7095            if (src1_needs_grads) {
7096                const int32_t s0    = ggml_get_op_params_i32(tensor, 0);
7097                const int32_t s1    = ggml_get_op_params_i32(tensor, 1);
7098                const int32_t p0    = ggml_get_op_params_i32(tensor, 2);
7099                const int32_t p1    = ggml_get_op_params_i32(tensor, 3);
7100                const int32_t d0    = ggml_get_op_params_i32(tensor, 4);
7101                const int32_t d1    = ggml_get_op_params_i32(tensor, 5);
7102                const bool    is_2D = ggml_get_op_params_i32(tensor, 6) == 1;
7103
7104                ggml_add_or_set(ctx, cgraph, isrc1, ggml_im2col_back(ctx, grad, src0, src1->ne, s0, s1, p0, p1, d0, d1, is_2D));
7105            }
7106        } break;
7107        case GGML_OP_POOL_2D: {
7108            if (src0_needs_grads) {
7109                const enum ggml_op_pool op = ggml_get_op_params_i32(tensor, 0);
7110                const      int32_t      k0 = ggml_get_op_params_i32(tensor, 1);
7111                const      int32_t      k1 = ggml_get_op_params_i32(tensor, 2);
7112                const      int32_t      s0 = ggml_get_op_params_i32(tensor, 3);
7113                const      int32_t      s1 = ggml_get_op_params_i32(tensor, 4);
7114                const      int32_t      p0 = ggml_get_op_params_i32(tensor, 5);
7115                const      int32_t      p1 = ggml_get_op_params_i32(tensor, 6);
7116
7117                ggml_add_or_set(ctx, cgraph, isrc0, ggml_pool_2d_back(ctx, grad, src0, op, k0, k1, s0, s1, p0, p1));
7118            }
7119        } break;
7120        case GGML_OP_WIN_PART:
7121        case GGML_OP_WIN_UNPART:
7122        case GGML_OP_UNARY: {
7123            switch (ggml_get_unary_op(tensor)) {
7124                case GGML_UNARY_OP_ABS: {
7125                    if (src0_needs_grads) {
7126                        ggml_add_or_set(ctx, cgraph, isrc0, ggml_mul(ctx, ggml_sgn(ctx, src0), grad));
7127                    }
7128                } break;
7129                case GGML_UNARY_OP_SGN: {
7130                    // noop
7131                } break;
7132                case GGML_UNARY_OP_NEG: {
7133                    if (src0_needs_grads) {
7134                        ggml_sub_or_set(ctx, cgraph, isrc0, grad);
7135                    }
7136                } break;
7137                case GGML_UNARY_OP_STEP: {
7138                    // noop
7139                } break;
7140                case GGML_UNARY_OP_RELU: {
7141                    if (src0_needs_grads) {
7142                        ggml_add_or_set(ctx, cgraph, isrc0, ggml_mul(ctx, ggml_step(ctx, src0), grad));
7143                    }
7144                } break;
7145                case GGML_UNARY_OP_SILU: {
7146                    if (src0_needs_grads) {
7147                        ggml_add_or_set(ctx, cgraph, isrc0, ggml_silu_back(ctx, grad, src0));
7148                    }
7149                } break;
7150                case GGML_UNARY_OP_EXP: {
7151                    if (src0_needs_grads) {
7152                        ggml_add_or_set(ctx, cgraph, isrc0, ggml_mul(ctx, tensor, grad));
7153                    }
7154                } break;
7155                case GGML_UNARY_OP_EXPM1: {
7156                    if (src0_needs_grads) {
7157                        ggml_add_or_set(ctx, cgraph, isrc0, ggml_mul(ctx, grad, ggml_exp(ctx, src0)));
7158                    }
7159                } break;
7160                case GGML_UNARY_OP_SOFTPLUS: {
7161                    if (src0_needs_grads) {
7162                        ggml_add_or_set(ctx, cgraph, isrc0, ggml_mul(ctx, grad, ggml_sigmoid(ctx, src0)));
7163                    }
7164                } break;
7165                default: {
7166                    fprintf(stderr, "%s: unsupported unary op for backward pass: %s\n",
7167                        __func__, ggml_unary_op_name(ggml_get_unary_op(tensor)));
7168                    GGML_ABORT("fatal error");
7169                } //break;
7170            }
7171        } break;
7172        case GGML_OP_CROSS_ENTROPY_LOSS: {
7173            if (src0_needs_grads) {
7174                ggml_add_or_set(ctx, cgraph, isrc0, ggml_cross_entropy_loss_back(ctx, grad, src0, src1));
7175            }
7176            GGML_ASSERT(!src1_needs_grads && "backward pass for labels not implemented");
7177        } break;
7178        case GGML_OP_GLU: {
7179            switch (ggml_get_glu_op(tensor)) {
7180                case GGML_GLU_OP_SWIGLU: {
7181                    if (src0_needs_grads) {
7182                        GGML_ASSERT(src1 && "backward pass only implemented for split swiglu");
7183                        ggml_add_or_set(ctx, cgraph, isrc0, ggml_silu_back(ctx, ggml_mul(ctx, grad, src1), src0));
7184                    }
7185                    if (src1_needs_grads) {
7186                        ggml_add_or_set(ctx, cgraph, isrc1, ggml_mul(ctx, ggml_silu(ctx, src0), grad));
7187                    }
7188                } break;
7189                default: {
7190                    GGML_ABORT("unsupported glu op for backward pass: %s", ggml_glu_op_name(ggml_get_glu_op(tensor)));
7191                } //break;
7192            }
7193        } break;
7194        case GGML_OP_NONE: {
7195            // noop
7196        } break;
7197        case GGML_OP_COUNT:
7198        default: {
7199            GGML_ABORT("%s: unsupported ggml op for backward pass: %s\n", __func__, ggml_op_name(tensor->op));
7200        } //break;
7201    }
7202
7203    GGML_ASSERT(!src0_needs_grads || ggml_are_same_shape(src0, cgraph->grads[isrc0]));
7204    GGML_ASSERT(!src1_needs_grads || ggml_are_same_shape(src1, cgraph->grads[isrc1]));
7205    GGML_ASSERT(!src2_needs_grads || ggml_are_same_shape(src2, cgraph->grads[isrc2]));
7206}
7207
7208static size_t ggml_visit_parents_graph(struct ggml_cgraph * cgraph, struct ggml_tensor * node, bool compute) {
7209    if (node->op != GGML_OP_NONE && compute) {
7210        node->flags |= GGML_TENSOR_FLAG_COMPUTE;
7211    }
7212
7213    const size_t node_hash_pos = ggml_hash_find(&cgraph->visited_hash_set, node);
7214    GGML_ASSERT(node_hash_pos != GGML_HASHSET_FULL);
7215
7216    if (ggml_bitset_get(cgraph->visited_hash_set.used, node_hash_pos)) {
7217        // already visited
7218
7219        if (compute) {
7220            // update the compute flag regardless
7221            for (int i = 0; i < GGML_MAX_SRC; ++i) {
7222                struct ggml_tensor * src = node->src[i];
7223                if (src && ((src->flags & GGML_TENSOR_FLAG_COMPUTE) == 0)) {
7224                    ggml_visit_parents_graph(cgraph, src, true);
7225                }
7226            }
7227        }
7228
7229        return node_hash_pos;
7230    }
7231
7232    // This is the first time we see this node in the current graph.
7233    cgraph->visited_hash_set.keys[node_hash_pos] = node;
7234    ggml_bitset_set(cgraph->visited_hash_set.used, node_hash_pos);
7235    cgraph->use_counts[node_hash_pos] = 0;
7236
7237    for (int i = 0; i < GGML_MAX_SRC; ++i) {
7238        const int k =
7239            (cgraph->order == GGML_CGRAPH_EVAL_ORDER_LEFT_TO_RIGHT) ? i :
7240            (cgraph->order == GGML_CGRAPH_EVAL_ORDER_RIGHT_TO_LEFT) ? (GGML_MAX_SRC-1-i) :
7241            /* unknown order, just fall back to using i */ i;
7242
7243        struct ggml_tensor * src = node->src[k];
7244        if (src) {
7245            const size_t src_hash_pos = ggml_visit_parents_graph(cgraph, src, compute);
7246
7247            // Update the use count for this operand.
7248            cgraph->use_counts[src_hash_pos]++;
7249        }
7250    }
7251
7252    if (node->op == GGML_OP_NONE && !(node->flags & GGML_TENSOR_FLAG_PARAM)) {
7253        // reached a leaf node, not part of the gradient graph (e.g. a constant)
7254        GGML_ASSERT(cgraph->n_leafs < cgraph->size);
7255
7256        if (strlen(node->name) == 0) {
7257            ggml_format_name(node, "leaf_%d", cgraph->n_leafs);
7258        }
7259
7260        cgraph->leafs[cgraph->n_leafs] = node;
7261        cgraph->n_leafs++;
7262    } else {
7263        GGML_ASSERT(cgraph->n_nodes < cgraph->size);
7264
7265        if (strlen(node->name) == 0) {
7266            ggml_format_name(node, "node_%d", cgraph->n_nodes);
7267        }
7268
7269        cgraph->nodes[cgraph->n_nodes] = node;
7270        cgraph->n_nodes++;
7271    }
7272
7273    return node_hash_pos;
7274}
7275
7276static void ggml_build_forward_impl(struct ggml_cgraph * cgraph, struct ggml_tensor * tensor, bool expand, bool compute) {
7277    if (!expand) {
7278        // TODO: this branch isn't accessible anymore, maybe move this to ggml_build_forward_expand
7279        ggml_graph_clear(cgraph);
7280    }
7281
7282    const int n_old = cgraph->n_nodes;
7283
7284    ggml_visit_parents_graph(cgraph, tensor, compute);
7285
7286    const int n_new = cgraph->n_nodes - n_old;
7287    GGML_PRINT_DEBUG("%s: visited %d new nodes\n", __func__, n_new);
7288
7289    if (n_new > 0) {
7290        // the last added node should always be starting point
7291        GGML_ASSERT(cgraph->nodes[cgraph->n_nodes - 1] == tensor);
7292    }
7293}
7294
7295struct ggml_tensor * ggml_build_forward_select(
7296        struct ggml_cgraph  * cgraph,
7297        struct ggml_tensor ** tensors,
7298        int                   n_tensors,
7299        int                   idx) {
7300    GGML_ASSERT(idx >= 0 && idx < n_tensors);
7301
7302    for (int i = 0; i < n_tensors; i++) {
7303        ggml_build_forward_impl(cgraph, tensors[i], true, i == idx ? true : false);
7304    }
7305
7306    return tensors[idx];
7307}
7308
7309void ggml_build_forward_expand(struct ggml_cgraph * cgraph, struct ggml_tensor * tensor) {
7310    ggml_build_forward_impl(cgraph, tensor, true, true);
7311}
7312
7313void ggml_build_forward_order(struct ggml_cgraph * cgraph, struct ggml_tensor * tensor) {
7314    ggml_build_forward_impl(cgraph, tensor, true, false);
7315}
7316
7317void ggml_build_backward_expand(
7318        struct ggml_context *  ctx,
7319        struct ggml_cgraph  *  cgraph,
7320        struct ggml_tensor  ** grad_accs) {
7321    GGML_ASSERT(cgraph->n_nodes > 0);
7322    GGML_ASSERT(cgraph->grads);
7323    GGML_ASSERT(cgraph->grad_accs);
7324
7325    const int n_nodes_f = cgraph->n_nodes;
7326
7327    memset(cgraph->grads,     0, cgraph->visited_hash_set.size*sizeof(struct ggml_tensor *));
7328    memset(cgraph->grad_accs, 0, cgraph->visited_hash_set.size*sizeof(struct ggml_tensor *));
7329    bool * grads_needed = calloc(cgraph->visited_hash_set.size, sizeof(bool));
7330
7331    {
7332        bool any_params = false;
7333        bool any_loss   = false;
7334        for (int i = 0; i < n_nodes_f; ++i) {
7335            struct ggml_tensor * node = cgraph->nodes[i];
7336            any_params = any_params || (node->flags & GGML_TENSOR_FLAG_PARAM);
7337            any_loss   = any_loss   || (node->flags & GGML_TENSOR_FLAG_LOSS);
7338        }
7339        GGML_ASSERT(any_params && "no trainable parameters found, did you forget to call ggml_set_param?");
7340        GGML_ASSERT(any_loss && "no training loss found, did you forget to call ggml_set_loss?");
7341    }
7342
7343    for (int i = 0; i < n_nodes_f; ++i) {
7344        struct ggml_tensor * node = cgraph->nodes[i];
7345
7346        if (node->type == GGML_TYPE_I32) {
7347            continue;
7348        }
7349
7350        bool node_needs_grad = (node->flags & GGML_TENSOR_FLAG_PARAM) || (node->flags & GGML_TENSOR_FLAG_LOSS);
7351        bool ignore_src[GGML_MAX_SRC] = {false};
7352        switch (node->op) {
7353            // gradients in node->src[0] for one reason or another have no effect on output gradients
7354            case GGML_OP_IM2COL:      // only used for its shape
7355            case GGML_OP_IM2COL_BACK: // same as IM2COL
7356                ignore_src[0] = true;
7357                break;
7358            case GGML_OP_UNARY: {
7359                const enum ggml_unary_op uop = ggml_get_unary_op(node);
7360                // SGN and STEP unary ops are piecewise constant
7361                if (uop == GGML_UNARY_OP_SGN || uop == GGML_UNARY_OP_STEP) {
7362                    ignore_src[0] = true;
7363                }
7364            } break;
7365
7366            // gradients in node->src[1] for one reason or another have no effect on output gradients
7367            case GGML_OP_CPY:           // gradients in CPY target are irrelevant
7368            case GGML_OP_GET_ROWS:      // row indices not differentiable
7369            case GGML_OP_GET_ROWS_BACK: // same as for GET_ROWS
7370            case GGML_OP_ROPE:          // positions not differentiable
7371                ignore_src[1] = true;
7372                break;
7373
7374            default:
7375                break;
7376        }
7377        for (int j = 0; j < GGML_MAX_SRC; ++j) {
7378            if (!node->src[j] || ignore_src[j] || !grads_needed[ggml_hash_find(&cgraph->visited_hash_set, node->src[j])]) {
7379                continue;
7380            }
7381            GGML_ASSERT(node->src[j]->type == GGML_TYPE_F32 || node->src[j]->type == GGML_TYPE_F16);
7382            node_needs_grad = true;
7383            break;
7384        }
7385        if (!node_needs_grad) {
7386            continue;
7387        }
7388
7389        // inplace operations are currently not supported
7390        GGML_ASSERT(!node->view_src || node->op == GGML_OP_CPY || node->op == GGML_OP_SET_ROWS || node->op == GGML_OP_VIEW ||
7391            node->op == GGML_OP_RESHAPE || node->op == GGML_OP_PERMUTE || node->op == GGML_OP_TRANSPOSE);
7392
7393        const size_t ihash = ggml_hash_find(&cgraph->visited_hash_set, node);
7394        GGML_ASSERT(ihash != GGML_HASHSET_FULL);
7395        GGML_ASSERT(ggml_bitset_get(cgraph->visited_hash_set.used, ihash));
7396        if (grad_accs && grad_accs[i]) {
7397            cgraph->grad_accs[ihash] = grad_accs[i];
7398            cgraph->grads[ihash]     = cgraph->grad_accs[ihash];
7399        } else if (node->flags & GGML_TENSOR_FLAG_LOSS) {
7400            // loss tensors always need a gradient accumulator
7401            cgraph->grad_accs[ihash] = ggml_new_tensor(ctx, GGML_TYPE_F32, GGML_MAX_DIMS, node->ne);
7402            cgraph->grads[ihash]     = cgraph->grad_accs[ihash];
7403        }
7404        grads_needed[ihash] = true;
7405    }
7406
7407    for (int i = n_nodes_f - 1; i >= 0; --i) {
7408        // inplace operations to add gradients are not created by ggml_compute_backward except for gradient accumulation
7409        // use allocator to automatically make inplace operations
7410        ggml_compute_backward(ctx, cgraph, i, grads_needed);
7411    }
7412
7413    free(grads_needed);
7414}
7415
7416static void * incr_ptr_aligned(void ** p, size_t size, size_t align) {
7417    void * ptr = *p;
7418    ptr = (void *) GGML_PAD((uintptr_t) ptr, align);
7419    *p = (void *) ((char *) ptr + size);
7420    return ptr;
7421}
7422
7423static size_t ggml_graph_nbytes(size_t size, bool grads) {
7424    size_t hash_size = ggml_hash_size(size * 2);
7425    void * p = 0;
7426    incr_ptr_aligned(&p, sizeof(struct ggml_cgraph), 1);
7427    incr_ptr_aligned(&p, size * sizeof(struct ggml_tensor *), sizeof(struct ggml_tensor *)); // nodes
7428    incr_ptr_aligned(&p, size * sizeof(struct ggml_tensor *), sizeof(struct ggml_tensor *)); // leafs
7429    incr_ptr_aligned(&p, hash_size * sizeof(int32_t), sizeof(int32_t)); // use_counts
7430    incr_ptr_aligned(&p, hash_size * sizeof(struct ggml_tensor *), sizeof(struct ggml_tensor *)); // hash keys
7431    if (grads) {
7432        incr_ptr_aligned(&p, hash_size * sizeof(struct ggml_tensor *), sizeof(struct ggml_tensor *)); // grads
7433        incr_ptr_aligned(&p, hash_size * sizeof(struct ggml_tensor *), sizeof(struct ggml_tensor *)); // grad_accs
7434    }
7435    incr_ptr_aligned(&p, ggml_bitset_size(hash_size) * sizeof(ggml_bitset_t), sizeof(ggml_bitset_t));
7436
7437    size_t nbytes = (size_t) p;
7438    return nbytes;
7439}
7440
7441size_t ggml_graph_overhead_custom(size_t size, bool grads) {
7442    return GGML_OBJECT_SIZE + GGML_PAD(ggml_graph_nbytes(size, grads), GGML_MEM_ALIGN);
7443}
7444
7445size_t ggml_graph_overhead(void) {
7446    return ggml_graph_overhead_custom(GGML_DEFAULT_GRAPH_SIZE, false);
7447}
7448
7449struct ggml_cgraph * ggml_new_graph_custom(struct ggml_context * ctx, size_t size, bool grads) {
7450    const size_t obj_size = ggml_graph_nbytes(size, grads);
7451    struct ggml_object * obj = ggml_new_object(ctx, GGML_OBJECT_TYPE_GRAPH, obj_size);
7452    struct ggml_cgraph * cgraph = (struct ggml_cgraph *) ((char *) ctx->mem_buffer + obj->offs);
7453
7454    // the size of the hash table is doubled since it needs to hold both nodes and leafs
7455    size_t hash_size = ggml_hash_size(size * 2);
7456
7457    void * p = cgraph + 1;
7458
7459    struct ggml_tensor ** nodes_ptr      =         incr_ptr_aligned(&p, size      * sizeof(struct ggml_tensor *), sizeof(struct ggml_tensor *));
7460    struct ggml_tensor ** leafs_ptr      =         incr_ptr_aligned(&p, size      * sizeof(struct ggml_tensor *), sizeof(struct ggml_tensor *));
7461    int32_t             * use_counts_ptr =         incr_ptr_aligned(&p, hash_size * sizeof(int32_t), sizeof(int32_t));
7462    struct ggml_tensor ** hash_keys_ptr  =         incr_ptr_aligned(&p, hash_size * sizeof(struct ggml_tensor *), sizeof(struct ggml_tensor *));
7463    struct ggml_tensor ** grads_ptr      = grads ? incr_ptr_aligned(&p, hash_size * sizeof(struct ggml_tensor *), sizeof(struct ggml_tensor *)) : NULL;
7464    struct ggml_tensor ** grad_accs_ptr  = grads ? incr_ptr_aligned(&p, hash_size * sizeof(struct ggml_tensor *), sizeof(struct ggml_tensor *)) : NULL;
7465
7466    ggml_bitset_t * hash_used = incr_ptr_aligned(&p, ggml_bitset_size(hash_size) * sizeof(ggml_bitset_t), sizeof(ggml_bitset_t));
7467
7468    // check that we allocated the correct amount of memory
7469    assert(obj_size == (size_t)((char *)p - (char *)cgraph));
7470
7471    *cgraph = (struct ggml_cgraph) {
7472        /*.size         =*/ size,
7473        /*.n_nodes      =*/ 0,
7474        /*.n_leafs      =*/ 0,
7475        /*.nodes        =*/ nodes_ptr,
7476        /*.grads        =*/ grads_ptr,
7477        /*.grad_accs    =*/ grad_accs_ptr,
7478        /*.leafs        =*/ leafs_ptr,
7479        /*.use_counts   =*/ use_counts_ptr,
7480        /*.hash_table   =*/ { hash_size, hash_used, hash_keys_ptr },
7481        /*.order        =*/ GGML_CGRAPH_EVAL_ORDER_LEFT_TO_RIGHT,
7482        /*.uid          =*/ 0,
7483    };
7484
7485    ggml_hash_set_reset(&cgraph->visited_hash_set);
7486    if (grads) {
7487        memset(cgraph->grads,     0, hash_size*sizeof(struct ggml_tensor *));
7488        memset(cgraph->grad_accs, 0, hash_size*sizeof(struct ggml_tensor *));
7489    }
7490
7491    return cgraph;
7492}
7493
7494struct ggml_cgraph * ggml_new_graph(struct ggml_context * ctx) {
7495    return ggml_new_graph_custom(ctx, GGML_DEFAULT_GRAPH_SIZE, false);
7496}
7497
7498struct ggml_cgraph ggml_graph_view(struct ggml_cgraph * cgraph0, int i0, int i1) {
7499    struct ggml_cgraph cgraph = {
7500        /*.size             =*/ 0,
7501        /*.n_nodes          =*/ i1 - i0,
7502        /*.n_leafs          =*/ 0,
7503        /*.nodes            =*/ cgraph0->nodes + i0,
7504        /*.grads            =*/ NULL, // gradients would need visited_hash_set
7505        /*.grad_accs        =*/ NULL,
7506        /*.leafs            =*/ NULL,
7507        /*.use_counts       =*/ cgraph0->use_counts,
7508        /*.visited_hash_set =*/ cgraph0->visited_hash_set,
7509        /*.order            =*/ cgraph0->order,
7510        /*.uid              =*/ 0
7511    };
7512
7513    return cgraph;
7514}
7515
7516void ggml_graph_cpy(struct ggml_cgraph * src, struct ggml_cgraph * dst) {
7517    GGML_ASSERT(dst->size >= src->n_leafs);
7518    GGML_ASSERT(dst->size >= src->n_nodes);
7519    GGML_ASSERT(dst->visited_hash_set.size >= src->visited_hash_set.size);
7520
7521    dst->n_leafs = src->n_leafs;
7522    dst->n_nodes = src->n_nodes;
7523    dst->order   = src->order;
7524
7525    for (int i = 0; i < src->n_leafs; ++i) {
7526        dst->leafs[i] = src->leafs[i];
7527    }
7528
7529    for (int i = 0; i < src->n_nodes; ++i) {
7530        dst->nodes[i] = src->nodes[i];
7531    }
7532
7533    for (size_t i = 0; i < src->visited_hash_set.size; ++i) {
7534        // copy all hashset keys (tensors) that are in use
7535        if (ggml_bitset_get(src->visited_hash_set.used, i)) {
7536            size_t new_hash_pos = ggml_hash_insert(&dst->visited_hash_set, src->visited_hash_set.keys[i]);
7537            dst->use_counts[new_hash_pos] = src->use_counts[i];
7538        }
7539    }
7540
7541    if (dst->grads) {
7542        memset(dst->grads,     0, dst->visited_hash_set.size*sizeof(struct ggml_tensor *));
7543        memset(dst->grad_accs, 0, dst->visited_hash_set.size*sizeof(struct ggml_tensor *));
7544    }
7545    if (src->grads) {
7546        GGML_ASSERT(dst->grads     != NULL);
7547        GGML_ASSERT(dst->grad_accs != NULL);
7548        for (int i = 0; i < src->n_nodes; ++i) {
7549            const size_t igrad_src = ggml_hash_find(&src->visited_hash_set, src->nodes[i]);
7550            const size_t igrad_dst = ggml_hash_find(&dst->visited_hash_set, dst->nodes[i]);
7551
7552            GGML_ASSERT(igrad_src != GGML_HASHSET_FULL);
7553            GGML_ASSERT(ggml_bitset_get(src->visited_hash_set.used, igrad_src));
7554            GGML_ASSERT(igrad_dst != GGML_HASHSET_FULL);
7555            GGML_ASSERT(ggml_bitset_get(dst->visited_hash_set.used, igrad_dst));
7556
7557            dst->grads[igrad_dst]     = src->grads[igrad_src];
7558            dst->grad_accs[igrad_dst] = src->grad_accs[igrad_src];
7559        }
7560    }
7561}
7562
7563struct ggml_cgraph * ggml_graph_dup(struct ggml_context * ctx, struct ggml_cgraph * cgraph, bool force_grads) {
7564    struct ggml_cgraph * result = ggml_new_graph_custom(ctx, cgraph->size, cgraph->grads || force_grads);
7565    ggml_graph_cpy(cgraph, result);
7566    return result;
7567}
7568
7569struct ggml_tensor * ggml_set_zero(struct ggml_tensor * tensor) {
7570    if (ggml_is_empty(tensor)) {
7571        return tensor;
7572    }
7573    if (tensor->buffer) {
7574        ggml_backend_tensor_memset(tensor, 0, 0, ggml_nbytes(tensor));
7575    } else {
7576        GGML_ASSERT(tensor->data);
7577        memset(tensor->data, 0, ggml_nbytes(tensor));
7578    }
7579    return tensor;
7580}
7581
7582void ggml_graph_reset(struct ggml_cgraph * cgraph) {
7583    if (!cgraph) {
7584        return;
7585    }
7586    GGML_ASSERT(cgraph->grads != NULL);
7587
7588    for (int i = 0; i < cgraph->n_nodes; i++) {
7589        struct ggml_tensor * node     = cgraph->nodes[i];
7590        struct ggml_tensor * grad_acc = ggml_graph_get_grad_acc(cgraph, node);
7591
7592        if (node->op == GGML_OP_OPT_STEP_ADAMW) {
7593            // clear momenta
7594            ggml_set_zero(node->src[2]);
7595            ggml_set_zero(node->src[3]);
7596        }
7597
7598        // initial gradients of loss should be 1, 0 otherwise
7599        if (grad_acc) {
7600            if (node->flags & GGML_TENSOR_FLAG_LOSS) {
7601                GGML_ASSERT(grad_acc->type == GGML_TYPE_F32);
7602                GGML_ASSERT(ggml_is_scalar(grad_acc));
7603
7604                const float onef = 1.0f;
7605                if (grad_acc->buffer) {
7606                    ggml_backend_tensor_set(grad_acc, &onef, 0, sizeof(float));
7607                } else {
7608                    GGML_ASSERT(grad_acc->data);
7609                    *((float *) grad_acc->data) = onef;
7610                }
7611            } else {
7612                ggml_set_zero(grad_acc);
7613            }
7614        }
7615    }
7616}
7617
7618void ggml_graph_clear(struct ggml_cgraph * cgraph) {
7619    cgraph->n_leafs = 0;
7620    cgraph->n_nodes = 0;
7621    ggml_hash_set_reset(&cgraph->visited_hash_set);
7622}
7623
7624int ggml_graph_size(struct ggml_cgraph * cgraph) {
7625    return cgraph->size;
7626}
7627
7628struct ggml_tensor * ggml_graph_node(struct ggml_cgraph * cgraph, int i) {
7629    if (i < 0) {
7630        GGML_ASSERT(cgraph->n_nodes + i >= 0);
7631        return cgraph->nodes[cgraph->n_nodes + i];
7632    }
7633
7634    GGML_ASSERT(i < cgraph->n_nodes);
7635    return cgraph->nodes[i];
7636}
7637
7638struct ggml_tensor ** ggml_graph_nodes(struct ggml_cgraph * cgraph) {
7639    return cgraph->nodes;
7640}
7641
7642int ggml_graph_n_nodes(struct ggml_cgraph * cgraph) {
7643    return cgraph->n_nodes;
7644}
7645
7646void ggml_graph_add_node(struct ggml_cgraph * cgraph, struct ggml_tensor * tensor) {
7647    GGML_ASSERT(cgraph->size > cgraph->n_nodes);
7648    cgraph->nodes[cgraph->n_nodes] = tensor;
7649    cgraph->n_nodes++;
7650}
7651
7652struct ggml_tensor * ggml_graph_get_tensor(const struct ggml_cgraph * cgraph, const char * name) {
7653    for (int i = 0; i < cgraph->n_leafs; i++) {
7654        struct ggml_tensor * leaf = cgraph->leafs[i];
7655
7656        if (strcmp(leaf->name, name) == 0) {
7657            return leaf;
7658        }
7659    }
7660
7661    for (int i = 0; i < cgraph->n_nodes; i++) {
7662        struct ggml_tensor * node = cgraph->nodes[i];
7663
7664        if (strcmp(node->name, name) == 0) {
7665            return node;
7666        }
7667    }
7668
7669    return NULL;
7670}
7671
7672struct ggml_tensor * ggml_graph_get_grad(const struct ggml_cgraph * cgraph, const struct ggml_tensor * node) {
7673    const size_t igrad = ggml_hash_find(&cgraph->visited_hash_set, node);
7674    return igrad != GGML_HASHSET_FULL && ggml_bitset_get(cgraph->visited_hash_set.used, igrad) && cgraph->grads ? cgraph->grads[igrad] : NULL;
7675}
7676
7677struct ggml_tensor * ggml_graph_get_grad_acc(const struct ggml_cgraph * cgraph, const struct ggml_tensor * node) {
7678    const size_t igrad = ggml_hash_find(&cgraph->visited_hash_set, node);
7679    return igrad != GGML_HASHSET_FULL && ggml_bitset_get(cgraph->visited_hash_set.used, igrad) && cgraph->grad_accs ? cgraph->grad_accs[igrad] : NULL;
7680}
7681
7682void ggml_graph_print(const struct ggml_cgraph * cgraph) {
7683    GGML_LOG_INFO("=== GRAPH ===\n");
7684
7685    GGML_LOG_INFO("n_nodes = %d\n", cgraph->n_nodes);
7686    for (int i = 0; i < cgraph->n_nodes; i++) {
7687        struct ggml_tensor * node = cgraph->nodes[i];
7688
7689        GGML_LOG_INFO(" - %3d: [ %5" PRId64 ", %5" PRId64 ", %5" PRId64 "] %16s %s\n",
7690                i,
7691                node->ne[0], node->ne[1], node->ne[2],
7692                ggml_op_name(node->op), (node->flags & GGML_TENSOR_FLAG_PARAM) ? "x" :
7693                      ggml_graph_get_grad(cgraph, node) ? "g" : " ");
7694    }
7695
7696    GGML_LOG_INFO("n_leafs = %d\n", cgraph->n_leafs);
7697    for (int i = 0; i < cgraph->n_leafs; i++) {
7698        struct ggml_tensor * node = cgraph->leafs[i];
7699
7700        GGML_LOG_INFO(" - %3d: [ %5" PRId64 ", %5" PRId64 "] %8s %16s\n",
7701                i,
7702                node->ne[0], node->ne[1],
7703                ggml_op_name(node->op),
7704                ggml_get_name(node));
7705    }
7706
7707    GGML_LOG_INFO("========================================\n");
7708}
7709
7710static int ggml_node_list_find_tensor(const struct ggml_cgraph * cgraph,
7711                                      const int *                idxs,
7712                                      int                        count,
7713                                      const struct ggml_tensor * tensor) {
7714    GGML_ASSERT(cgraph && idxs);
7715    for (int i = 0; i < count; ++i) {
7716        const int node_idx = idxs[i];
7717
7718        if (node_idx >= cgraph->n_nodes) {
7719            return -1;
7720        }
7721        if (cgraph->nodes[node_idx] == tensor) {
7722            return i;
7723        }
7724    }
7725    return -1;
7726}
7727
7728static bool ggml_is_constant(const struct ggml_tensor * tensor) {
7729    return tensor->buffer != NULL && ggml_backend_buffer_get_usage(tensor->buffer) == GGML_BACKEND_BUFFER_USAGE_WEIGHTS && (tensor->flags & GGML_TENSOR_FLAG_PARAM) == 0;
7730}
7731
7732bool ggml_can_fuse_subgraph_ext(const struct ggml_cgraph * cgraph,
7733                                const int *                node_idxs,
7734                                int                        count,
7735                                const enum ggml_op *       ops,
7736                                const int *                outputs,
7737                                int                        num_outputs) {
7738    GGML_ASSERT(outputs && num_outputs > 0);
7739
7740    for (int i = 0; i < count; ++i) {
7741        if (node_idxs[i] >= cgraph->n_nodes) {
7742            return false;
7743        }
7744
7745        const struct ggml_tensor * node = cgraph->nodes[node_idxs[i]];
7746
7747        if (node->op != ops[i]) {
7748            return false;
7749        }
7750
7751        if ((node->flags & GGML_TENSOR_FLAG_COMPUTE) == 0) {
7752            return false;
7753        }
7754
7755        if (ggml_node_list_find_tensor(cgraph, outputs, num_outputs, node) != -1) {
7756            continue;
7757        }
7758
7759        if (node->flags & GGML_TENSOR_FLAG_OUTPUT) {
7760            return false;
7761        }
7762
7763        int subgraph_uses = 0;
7764        for (int j = i + 1; j < count; ++j) {
7765            const struct ggml_tensor * other_node = cgraph->nodes[node_idxs[j]];
7766            for (int src_idx = 0; src_idx < GGML_MAX_SRC; src_idx++) {
7767                if (other_node->src[src_idx] == node) {
7768                    subgraph_uses++;
7769                }
7770            }
7771        }
7772
7773        if (subgraph_uses != ggml_node_get_use_count(cgraph, node_idxs[i])) {
7774            return false;
7775        }
7776
7777        // if node is a view, check if the view_src and all its parent view_srcs are within the subgraph.
7778        // external view sources are allowed only for weight tensors, which are constant for this graph execution.
7779        struct ggml_tensor * view_src = node->view_src;
7780        while (view_src) {
7781            if (ggml_node_list_find_tensor(cgraph, node_idxs, count, view_src) == -1 && !ggml_is_constant(view_src)) {
7782                return false;
7783            }
7784            view_src = view_src->view_src;
7785        }
7786    }
7787
7788    return true;
7789}
7790
7791// check if node is part of the graph
7792static bool ggml_graph_find(const struct ggml_cgraph * cgraph, const struct ggml_tensor * node) {
7793    if (cgraph == NULL) {
7794        return true;
7795    }
7796
7797    for (int i = 0; i < cgraph->n_nodes; i++) {
7798        if (cgraph->nodes[i] == node) {
7799            return true;
7800        }
7801    }
7802
7803    return false;
7804}
7805
7806static struct ggml_tensor * ggml_graph_get_parent(const struct ggml_cgraph * cgraph, const struct ggml_tensor * node) {
7807    for (int i = 0; i < cgraph->n_nodes; i++) {
7808        struct ggml_tensor * parent = cgraph->nodes[i];
7809        struct ggml_tensor * grad = ggml_graph_get_grad(cgraph, parent);
7810
7811        if (grad == node) {
7812            return parent;
7813        }
7814    }
7815
7816    return NULL;
7817}
7818
7819static void ggml_graph_dump_dot_node_edge(FILE * fp, const struct ggml_cgraph * gb, struct ggml_tensor * node, struct ggml_tensor * parent, const char * label)  {
7820    struct ggml_tensor * gparent = ggml_graph_get_parent(gb, node);
7821    struct ggml_tensor * gparent0 = ggml_graph_get_parent(gb, parent);
7822    fprintf(fp, "  \"%p\" -> \"%p\" [ arrowhead = %s; style = %s; label = \"%s\"; ]\n",
7823            gparent0 ? (void *) gparent0 : (void *) parent,
7824            gparent ? (void *) gparent : (void *) node,
7825            gparent ? "empty" : "vee",
7826            gparent ? "dashed" : "solid",
7827            label);
7828}
7829
7830static void ggml_graph_dump_dot_leaf_edge(FILE * fp, struct ggml_tensor * node, struct ggml_tensor * parent, const char * label)  {
7831    fprintf(fp, "  \"%p\" -> \"%p\" [ label = \"%s\"; ]\n",
7832            (void *) parent,
7833            (void *) node,
7834            label);
7835}
7836
7837void ggml_graph_dump_dot(const struct ggml_cgraph * gb, const struct ggml_cgraph * cgraph, const char * filename) {
7838    char color[16];
7839
7840    FILE * fp = ggml_fopen(filename, "w");
7841    GGML_ASSERT(fp);
7842
7843    fprintf(fp, "digraph G {\n");
7844    fprintf(fp, "  newrank = true;\n");
7845    fprintf(fp, "  rankdir = TB;\n");
7846
7847    for (int i = 0; i < gb->n_nodes; i++) {
7848        struct ggml_tensor * node = gb->nodes[i];
7849        struct ggml_tensor * grad = ggml_graph_get_grad(gb, node);
7850
7851        if (ggml_graph_get_parent(gb, node) != NULL) {
7852            continue;
7853        }
7854
7855        if (node->flags & GGML_TENSOR_FLAG_PARAM) {
7856            snprintf(color, sizeof(color), "yellow");
7857        } else if (grad) {
7858            if (ggml_graph_find(cgraph, node)) {
7859                snprintf(color, sizeof(color), "green");
7860            } else {
7861                snprintf(color, sizeof(color), "lightblue");
7862            }
7863        } else {
7864            snprintf(color, sizeof(color), "white");
7865        }
7866
7867        fprintf(fp, "  \"%p\" [ "
7868                    "style = filled; fillcolor = %s; shape = record; "
7869                    "label=\"",
7870                (void *) node, color);
7871
7872        if (strlen(node->name) > 0) {
7873            fprintf(fp, "%s (%s)|", node->name, ggml_type_name(node->type));
7874        } else {
7875            fprintf(fp, "(%s)|", ggml_type_name(node->type));
7876        }
7877
7878        if (ggml_is_matrix(node)) {
7879            fprintf(fp, "%d [%" PRId64 ", %" PRId64 "] | <x>%s", i, node->ne[0], node->ne[1], ggml_op_symbol(node->op));
7880        } else {
7881            fprintf(fp, "%d [%" PRId64 ", %" PRId64 ", %" PRId64 "] | <x>%s", i, node->ne[0], node->ne[1], node->ne[2], ggml_op_symbol(node->op));
7882        }
7883
7884        if (grad) {
7885            fprintf(fp, " | <g>%s\"; ]\n", ggml_op_symbol(grad->op));
7886        } else {
7887            fprintf(fp, "\"; ]\n");
7888        }
7889    }
7890
7891    for (int i = 0; i < gb->n_leafs; i++) {
7892        struct ggml_tensor * node = gb->leafs[i];
7893
7894        snprintf(color, sizeof(color), "pink");
7895
7896        fprintf(fp, "  \"%p\" [ "
7897                    "style = filled; fillcolor = %s; shape = record; "
7898                    "label=\"<x>",
7899                (void *) node, color);
7900
7901        if (strlen(node->name) > 0) {
7902            fprintf(fp, "%s (%s)|", node->name, ggml_type_name(node->type));
7903        } else {
7904            fprintf(fp, "(%s)|", ggml_type_name(node->type));
7905        }
7906
7907        fprintf(fp, "CONST %d [%" PRId64 ", %" PRId64 "]", i, node->ne[0], node->ne[1]);
7908        if (ggml_nelements(node) < 5 && node->data != NULL) {
7909            fprintf(fp, " | (");
7910            for (int j = 0; j < ggml_nelements(node); j++) {
7911                // FIXME: use ggml-backend to obtain the tensor data
7912                //if (node->type == GGML_TYPE_I8 || node->type == GGML_TYPE_I16 || node->type == GGML_TYPE_I32) {
7913                //    fprintf(fp, "%d", ggml_get_i32_1d(node, j));
7914                //}
7915                //else if (node->type == GGML_TYPE_F32 ||
7916                //         node->type == GGML_TYPE_F16 ||
7917                //         node->type == GGML_TYPE_BF16) {
7918                //    fprintf(fp, "%.1e", (double)ggml_get_f32_1d(node, j));
7919                //}
7920                //else
7921                {
7922                    fprintf(fp, "#");
7923                }
7924                if (j < ggml_nelements(node) - 1) {
7925                    fprintf(fp, ", ");
7926                }
7927            }
7928            fprintf(fp, ")");
7929        }
7930        fprintf(fp, "\"; ]\n");
7931    }
7932
7933    for (int i = 0; i < gb->n_nodes; i++) {
7934        struct ggml_tensor * node = gb->nodes[i];
7935
7936        for (int j = 0; j < GGML_MAX_SRC; j++) {
7937            if (node->src[j]) {
7938                char label[16];
7939                snprintf(label, sizeof(label), "src %d", j);
7940                ggml_graph_dump_dot_node_edge(fp, gb, node, node->src[j], label);
7941            }
7942        }
7943    }
7944
7945    for (int i = 0; i < gb->n_leafs; i++) {
7946        struct ggml_tensor * node = gb->leafs[i];
7947
7948        for (int j = 0; j < GGML_MAX_SRC; j++) {
7949            if (node->src[j]) {
7950                char label[16];
7951                snprintf(label, sizeof(label), "src %d", j);
7952                ggml_graph_dump_dot_leaf_edge(fp, node, node->src[j], label);
7953            }
7954        }
7955    }
7956
7957    fprintf(fp, "}\n");
7958
7959    fclose(fp);
7960
7961    GGML_LOG_INFO("%s: dot -Tpng %s -o %s.png && open %s.png\n", __func__, filename, filename, filename);
7962}
7963
7964////////////////////////////////////////////////////////////////////////////////
7965
7966void ggml_set_input(struct ggml_tensor * tensor) {
7967    tensor->flags |= GGML_TENSOR_FLAG_INPUT;
7968}
7969
7970void ggml_set_output(struct ggml_tensor * tensor) {
7971    for (struct ggml_tensor * cur = tensor; cur != NULL; cur = cur->view_src) {
7972        cur->flags |= GGML_TENSOR_FLAG_OUTPUT;
7973    }
7974}
7975
7976void ggml_set_param(struct ggml_tensor * tensor) {
7977    GGML_ASSERT(tensor->op == GGML_OP_NONE);
7978    tensor->flags |= GGML_TENSOR_FLAG_PARAM;
7979}
7980
7981void ggml_set_loss(struct ggml_tensor * tensor) {
7982    GGML_ASSERT(ggml_is_scalar(tensor));
7983    GGML_ASSERT(tensor->type == GGML_TYPE_F32);
7984    tensor->flags |= GGML_TENSOR_FLAG_LOSS;
7985}
7986
7987////////////////////////////////////////////////////////////////////////////////
7988
7989void ggml_quantize_init(enum ggml_type type) {
7990    ggml_critical_section_start();
7991
7992    switch (type) {
7993        case GGML_TYPE_IQ2_XXS:
7994        case GGML_TYPE_IQ2_XS:
7995        case GGML_TYPE_IQ2_S:
7996        case GGML_TYPE_IQ1_S:
7997        case GGML_TYPE_IQ1_M:   iq2xs_init_impl(type); break;
7998        case GGML_TYPE_IQ3_XXS: iq3xs_init_impl(256); break;
7999        case GGML_TYPE_IQ3_S:   iq3xs_init_impl(512); break;
8000        default: // nothing
8001            break;
8002    }
8003
8004    ggml_critical_section_end();
8005}
8006
8007void ggml_quantize_free(void) {
8008    ggml_critical_section_start();
8009
8010    iq2xs_free_impl(GGML_TYPE_IQ2_XXS);
8011    iq2xs_free_impl(GGML_TYPE_IQ2_XS);
8012    iq2xs_free_impl(GGML_TYPE_IQ2_S);
8013    iq2xs_free_impl(GGML_TYPE_IQ1_S);
8014    iq2xs_free_impl(GGML_TYPE_IQ1_M);
8015    iq3xs_free_impl(256);
8016    iq3xs_free_impl(512);
8017
8018    ggml_critical_section_end();
8019}
8020
8021bool ggml_quantize_requires_imatrix(enum ggml_type type) {
8022    return
8023        type == GGML_TYPE_IQ2_XXS ||
8024        type == GGML_TYPE_IQ2_XS  ||
8025        type == GGML_TYPE_IQ1_S;//   ||
8026        //type == GGML_TYPE_IQ1_M;
8027}
8028
8029size_t ggml_quantize_chunk(
8030        enum ggml_type   type,
8031           const float * src,
8032                  void * dst,
8033               int64_t   start,
8034               int64_t   nrows,
8035               int64_t   n_per_row,
8036           const float * imatrix) {
8037    const int64_t n = nrows * n_per_row;
8038
8039    if (ggml_quantize_requires_imatrix(type)) {
8040        GGML_ASSERT(imatrix != NULL);
8041    }
8042
8043    GGML_ASSERT(start % type_traits[type].blck_size == 0);
8044    GGML_ASSERT(start % n_per_row == 0);
8045
8046    ggml_quantize_init(type); // this is noop if already initialized
8047
8048    const size_t start_row = start / n_per_row;
8049    const size_t row_size  = ggml_row_size(type, n_per_row);
8050
8051    size_t result = 0;
8052
8053    switch (type) {
8054        case GGML_TYPE_Q1_0:    result = quantize_q1_0   (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8055        case GGML_TYPE_Q2_0:    result = quantize_q2_0   (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8056        case GGML_TYPE_Q4_0:    result = quantize_q4_0   (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8057        case GGML_TYPE_Q4_1:    result = quantize_q4_1   (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8058        case GGML_TYPE_Q5_0:    result = quantize_q5_0   (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8059        case GGML_TYPE_Q5_1:    result = quantize_q5_1   (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8060        case GGML_TYPE_Q8_0:    result = quantize_q8_0   (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8061        case GGML_TYPE_MXFP4:   result = quantize_mxfp4  (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8062        case GGML_TYPE_NVFP4:   result = quantize_nvfp4  (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8063        case GGML_TYPE_Q2_K:    result = quantize_q2_K   (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8064        case GGML_TYPE_Q3_K:    result = quantize_q3_K   (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8065        case GGML_TYPE_Q4_K:    result = quantize_q4_K   (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8066        case GGML_TYPE_Q5_K:    result = quantize_q5_K   (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8067        case GGML_TYPE_Q6_K:    result = quantize_q6_K   (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8068        case GGML_TYPE_TQ1_0:   result = quantize_tq1_0  (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8069        case GGML_TYPE_TQ2_0:   result = quantize_tq2_0  (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8070        case GGML_TYPE_IQ2_XXS: result = quantize_iq2_xxs(src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8071        case GGML_TYPE_IQ2_XS:  result = quantize_iq2_xs (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8072        case GGML_TYPE_IQ3_XXS: result = quantize_iq3_xxs(src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8073        case GGML_TYPE_IQ3_S:   result = quantize_iq3_s  (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8074        case GGML_TYPE_IQ2_S:   result = quantize_iq2_s  (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8075        case GGML_TYPE_IQ1_S:   result = quantize_iq1_s  (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8076        case GGML_TYPE_IQ1_M:   result = quantize_iq1_m  (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8077        case GGML_TYPE_IQ4_NL:  result = quantize_iq4_nl (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8078        case GGML_TYPE_IQ4_XS:  result = quantize_iq4_xs (src + start, (char *) dst + start_row * row_size, nrows, n_per_row, imatrix); break;
8079        case GGML_TYPE_F16:
8080            {
8081                size_t elemsize = sizeof(ggml_fp16_t);
8082                ggml_fp32_to_fp16_row(src + start, (ggml_fp16_t *)dst + start, n);
8083                result = n * elemsize;
8084            } break;
8085        case GGML_TYPE_BF16:
8086            {
8087                size_t elemsize = sizeof(ggml_bf16_t);
8088                ggml_fp32_to_bf16_row_ref(src + start, (ggml_bf16_t *)dst + start, n);
8089                result = n * elemsize;
8090            } break;
8091        case GGML_TYPE_F32:
8092            {
8093                size_t elemsize = sizeof(float);
8094                result = n * elemsize;
8095                memcpy((uint8_t *)dst + start * elemsize, src + start, result);
8096            } break;
8097        default:
8098            assert(false);
8099    }
8100
8101    GGML_ASSERT(result == nrows * row_size);
8102
8103    return result;
8104}
8105
8106////////////////////////////////////////////////////////////////////////////////
8107
8108void ggml_log_get(ggml_log_callback * log_callback, void ** user_data) {
8109    *log_callback = g_logger_state.log_callback;
8110    *user_data    = g_logger_state.log_callback_user_data;
8111}
8112
8113void ggml_log_set(ggml_log_callback log_callback, void * user_data) {
8114    g_logger_state.log_callback = log_callback ? log_callback : ggml_log_callback_default;
8115    g_logger_state.log_callback_user_data = user_data;
8116}
8117
8118void ggml_threadpool_params_init(struct ggml_threadpool_params * p, int n_threads) {
8119    p->n_threads  = n_threads;
8120    p->prio       = 0;     // default priority (usually means normal or inherited)
8121    p->poll       = 50;    // hybrid-polling enabled
8122    p->strict_cpu = false; // no strict placement (all threads share same cpumask)
8123    p->paused     = false; // threads are ready to go
8124    memset(p->cpumask, 0, GGML_MAX_N_THREADS); // all-zero means use the default affinity (usually inherited)
8125}
8126
8127struct ggml_threadpool_params ggml_threadpool_params_default(int n_threads) {
8128    struct ggml_threadpool_params p;
8129    ggml_threadpool_params_init(&p, n_threads);
8130    return p;
8131}
8132
8133bool ggml_threadpool_params_match(const struct ggml_threadpool_params * p0, const struct ggml_threadpool_params * p1) {
8134    if (p0->n_threads  != p1->n_threads  ) return false;
8135    if (p0->prio       != p1->prio       ) return false;
8136    if (p0->poll       != p1->poll       ) return false;
8137    if (p0->strict_cpu != p1->strict_cpu ) return false;
8138    return memcmp(p0->cpumask, p1->cpumask, GGML_MAX_N_THREADS) == 0;
8139}