| 1390 | } |
| 1391 | |
| 1392 | static void ggml_cl_mul_f32(const ggml_tensor * src0, const ggml_tensor * src1, ggml_tensor * dst) { |
| 1393 | GGML_ASSERT(src1->backend == GGML_BACKEND_GPU); |
| 1394 | const int64_t ne00 = src0->ne[0]; |
| 1395 | const int64_t ne01 = src0->ne[1]; |
| 1396 | const int64_t ne02 = src0->ne[2]; |
| 1397 | const int64_t ne03 = src0->ne[3]; |
| 1398 | const int64_t ne10 = src1->ne[0]; |
| 1399 | const int64_t ne11 = src1->ne[1]; |
| 1400 | const int64_t ne12 = src1->ne[2]; |
| 1401 | const int64_t ne13 = src1->ne[3]; |
| 1402 | const int nb2 = dst->nb[2]; |
| 1403 | const int nb3 = dst->nb[3]; |
| 1404 | size_t x_size; |
| 1405 | size_t d_size; |
| 1406 | |
| 1407 | cl_mem d_X = ggml_cl_pool_malloc(ne00 * ne01 * sizeof(float), &x_size); // src0 |
| 1408 | cl_mem d_Y = (cl_mem) src1->extra; // src1 is already on device, broadcasted. |
| 1409 | cl_mem d_D = ggml_cl_pool_malloc(ne00 * ne01 * sizeof(float), &d_size); // dst |
| 1410 | |
| 1411 | |
| 1412 | for (int64_t i03 = 0; i03 < ne03; i03++) { |
| 1413 | for (int64_t i02 = 0; i02 < ne02; i02++) { |
| 1414 | cl_event ev; |
| 1415 | |
| 1416 | // copy src0 to device |
| 1417 | CL_CHECK(ggml_cl_h2d_tensor_2d(queue, d_X, 0, src0, i03, i02, &ev)); |
| 1418 | |
| 1419 | const int64_t i13 = i03%ne13; |
| 1420 | const int64_t i12 = i02%ne12; |
| 1421 | const int i1 = i13*ne12*ne11 + i12*ne11; |
| 1422 | |
| 1423 | cl_int x_offset = 0; |
| 1424 | cl_int y_offset = i1*ne10; |
| 1425 | cl_int d_offset = 0; |
| 1426 | |
| 1427 | size_t global = ne00 * ne01; |
| 1428 | cl_int ky = ne10 * ne11; |
| 1429 | |
| 1430 | CL_CHECK(clSetKernelArg(mul_f32_cl, 0, sizeof(cl_mem), &d_X)); |
| 1431 | CL_CHECK(clSetKernelArg(mul_f32_cl, 1, sizeof(cl_int), &x_offset)); |
| 1432 | CL_CHECK(clSetKernelArg(mul_f32_cl, 2, sizeof(cl_mem), &d_Y)); |
| 1433 | CL_CHECK(clSetKernelArg(mul_f32_cl, 3, sizeof(cl_int), &y_offset)); |
| 1434 | CL_CHECK(clSetKernelArg(mul_f32_cl, 4, sizeof(cl_mem), &d_D)); |
| 1435 | CL_CHECK(clSetKernelArg(mul_f32_cl, 5, sizeof(cl_int), &d_offset)); |
| 1436 | CL_CHECK(clSetKernelArg(mul_f32_cl, 6, sizeof(cl_int), &ky)); |
| 1437 | CL_CHECK(clEnqueueNDRangeKernel(queue, mul_f32_cl, 1, NULL, &global, NULL, 1, &ev, NULL)); |
| 1438 | |
| 1439 | CL_CHECK(clReleaseEvent(ev)); |
| 1440 | CL_CHECK(clFinish(queue)); |
| 1441 | |
| 1442 | // copy dst to host |
| 1443 | float * d = (float *) ((char *) dst->data + i02*nb2 + i03*nb3); |
| 1444 | CL_CHECK(clEnqueueReadBuffer(queue, d_D, true, 0, sizeof(float) * ne00*ne01, d, 0, NULL, NULL)); |
| 1445 | } |
| 1446 | } |
| 1447 | ggml_cl_pool_free(d_X, x_size); |
| 1448 | ggml_cl_pool_free(d_D, d_size); |
| 1449 | } |
no test coverage detected