ufo-filter-scale.c 5.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172
  1. #include <gmodule.h>
  2. #ifdef __APPLE__
  3. #include <OpenCL/cl.h>
  4. #else
  5. #include <CL/cl.h>
  6. #endif
  7. #include <ufo/ufo-filter.h>
  8. #include <ufo/ufo-buffer.h>
  9. #include <ufo/ufo-resource-manager.h>
  10. #include "ufo-filter-scale.h"
  11. /**
  12. * SECTION:ufo-filter-scale
  13. * @Short_description: Scale image values
  14. * @Title: scale
  15. *
  16. * Scale input image values. The output
  17. * is a new image.
  18. * #UfoFilterScale: params.
  19. */
  20. struct _UfoFilterScalePrivate {
  21. float scale;
  22. cl_kernel kernel;
  23. };
  24. GType ufo_filter_scale_get_type(void) G_GNUC_CONST;
  25. G_DEFINE_TYPE(UfoFilterScale, ufo_filter_scale, UFO_TYPE_FILTER);
  26. #define UFO_FILTER_SCALE_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), UFO_TYPE_FILTER_SCALE, UfoFilterScalePrivate))
  27. enum {
  28. PROP_0 =0,
  29. PROP_SCALE,
  30. N_PROPERTIES
  31. };
  32. static GParamSpec *scale_properties[N_PROPERTIES] = { NULL, };
  33. /*
  34. * virtual methods
  35. */
  36. static void
  37. ufo_filter_scale_initialize(UfoFilter *filter, UfoBuffer *params[], guint **dim_sizes, GError **error)
  38. {
  39. UfoFilterScalePrivate *priv = UFO_FILTER_SCALE_GET_PRIVATE(filter);
  40. UfoResourceManager *manager = ufo_filter_get_resource_manager(filter);
  41. GError *tmp_error = NULL;
  42. priv->kernel = ufo_resource_manager_get_kernel(manager, "scale.cl", "scale", &tmp_error);
  43. if (tmp_error != NULL) {
  44. g_propagate_error (error, tmp_error);
  45. return;
  46. }
  47. guint xs, ys;
  48. ufo_buffer_get_2d_dimensions (params[0], &xs, &ys);
  49. dim_sizes[0][0] = xs;
  50. dim_sizes[0][1] = ys;
  51. }
  52. /*
  53. * This is the main method in which the filter processes one buffer after
  54. * another.
  55. */
  56. static void ufo_filter_scale_process_gpu(UfoFilter *filter, UfoBuffer *input[], UfoBuffer *output[], GError **error)
  57. {
  58. g_return_if_fail(UFO_IS_FILTER(filter));
  59. cl_command_queue command_queue = (cl_command_queue) ufo_filter_get_command_queue(filter);
  60. UfoFilterScalePrivate *priv = UFO_FILTER_SCALE_GET_PRIVATE(filter);
  61. guint xs, ys;
  62. ufo_buffer_get_2d_dimensions (input[0], &xs, &ys);
  63. size_t global_work_size[2] = {(size_t) xs, (size_t) ys};
  64. cl_mem input_mem = (cl_mem) ufo_buffer_get_device_array(input[0], command_queue);
  65. cl_mem output_mem = (cl_mem) ufo_buffer_get_device_array(output[0], command_queue);
  66. float scale = (float) priv->scale;
  67. cl_kernel kernel = priv->kernel;
  68. CHECK_OPENCL_ERROR(clSetKernelArg(kernel, 0, sizeof(cl_mem), (void *) &input_mem));
  69. CHECK_OPENCL_ERROR(clSetKernelArg(kernel, 1, sizeof(cl_mem), (void *) &output_mem));
  70. CHECK_OPENCL_ERROR(clSetKernelArg(kernel, 2, sizeof(int), &xs));
  71. CHECK_OPENCL_ERROR(clSetKernelArg(kernel, 3, sizeof(float), &scale));
  72. cl_event event;
  73. CHECK_OPENCL_ERROR(clEnqueueNDRangeKernel(command_queue, kernel,
  74. 2, NULL, global_work_size, NULL,
  75. 0, NULL, &event));
  76. clFinish(command_queue);
  77. }
  78. static void
  79. ufo_filter_scale_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec)
  80. {
  81. UfoFilterScale *self = UFO_FILTER_SCALE(object);
  82. switch (property_id) {
  83. case PROP_SCALE:
  84. self->priv->scale = (float) g_value_get_double(value);
  85. break;
  86. default:
  87. G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec);
  88. break;
  89. }
  90. }
  91. static void
  92. ufo_filter_scale_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec)
  93. {
  94. UfoFilterScale *self = UFO_FILTER_SCALE(object);
  95. switch (property_id) {
  96. case PROP_SCALE:
  97. g_value_set_double(value, (double) self->priv->scale);
  98. break;
  99. default:
  100. G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec);
  101. break;
  102. }
  103. }
  104. static void
  105. ufo_filter_scale_class_init(UfoFilterScaleClass *klass)
  106. {
  107. GObjectClass *gobject_class = G_OBJECT_CLASS(klass);
  108. UfoFilterClass *filter_class = UFO_FILTER_CLASS(klass);
  109. gobject_class->set_property = ufo_filter_scale_set_property;
  110. gobject_class->get_property = ufo_filter_scale_get_property;
  111. filter_class->initialize = ufo_filter_scale_initialize;
  112. filter_class->process_gpu = ufo_filter_scale_process_gpu;
  113. scale_properties[PROP_SCALE] =
  114. g_param_spec_double("scale",
  115. "Scale",
  116. "Scale for each pixel",
  117. -5.0, /* minimum */
  118. 10.0, /* maximum */
  119. 1.0, /* default */
  120. G_PARAM_READWRITE);
  121. g_object_class_install_property(gobject_class, PROP_SCALE, scale_properties[PROP_SCALE]);
  122. /* install private data */
  123. g_type_class_add_private(gobject_class, sizeof(UfoFilterScalePrivate));
  124. }
  125. static void
  126. ufo_filter_scale_init(UfoFilterScale *self)
  127. {
  128. UfoFilterScalePrivate *priv = self->priv = UFO_FILTER_SCALE_GET_PRIVATE(self);
  129. UfoInputParameter input_params[] = {{2, UFO_FILTER_INFINITE_INPUT}};
  130. UfoOutputParameter output_params[] = {{2}};
  131. priv->scale = 1.0;
  132. priv->kernel = NULL;
  133. ufo_filter_register_inputs (UFO_FILTER(self), 1, input_params);
  134. ufo_filter_register_outputs(UFO_FILTER(self), 1, output_params);
  135. }
  136. G_MODULE_EXPORT UfoFilter *ufo_filter_plugin_new(void)
  137. {
  138. return g_object_new(UFO_TYPE_FILTER_SCALE, NULL);
  139. }