কম্পিউটার টিউটোরিয়াল

স্টেপ-বাই-স্টেপ গাইড: পারফরম্যান্স এবং ইন্টিগ্রেশনের জন্য রুবি C এক্সটেনশন বিল্ড করা

একটি C এক্সটেনশন লেখা আপনাকে রুবির সাথে C থেকে ইন্টারঅ্যাক্ট করতে দেয়।

আপনি এটি করতে চাইতে পারেন যদি কোনো নির্দিষ্ট গুরুত্বপূর্ণ মেথড আছে जिसे আপনি C-এর গতি দিয়ে অপ্টিমাইজ করতে চান, অথবা যদি আপনি একটি C লাইব্রেরি এবং রুবির মধ্যে ইন্টারফেস তৈরি করতে চান।

একটি বিকল্প হবে FFI মডিউল ব্যবহার করা।

এখন:

আসুন শিখি কীভাবে একটি C এক্সটেনশন লিখবেন!

আপনার প্রথম C এক্সটেনশন

extconf.rb নামে একটি ফাইল তৈরি করুন এই কন্টেন্টসহ:

require 'mkmf'
create_header
create_makefile 'foobar'

তারপর ruby extconf.rb রান করুন যা আপনার জন্য কিছু ফাইল তৈরি করবে (Makefile এবং extconf.h)। এই ফাইলগুলো পরিবর্তন করবেন না।

এখন foobar.c তৈরি করুন, এই নামটি extconf.rb-এ create_makefile লাইন থেকে আসে। আপনি এটি পরিবর্তন করতে পারেন কিন্তু এটি আপনার .c ফাইলনেমের সাথে মিলতে হবে কাজ করার জন্য।

foobar.c-এর ভেতরে এটি যোগ করুন:

#include "ruby.h"
#include "extconf.h"
void Init_foobar() {
  // আপনার C কোড এখানে যাবে
}

এটি আপনার C এক্সটেনশনের বেসিক স্কেলেটন। লক্ষ্য করুন যে আপনাকে extconf.rb-এ ঘোষিত নামটি ব্যবহার করতে হবে প্লাস Init_ শব্দটি। এই কেসে Init_foobar।

আপনি make রান করে এটি কম্পাইল করতে পারেন, এবং আপনি যা পাবেন সেটি একটি so ফাইল যা আপনি আপনার রুবি অ্যাপ্লিকেশনে require দিয়ে লোড করতে পারেন।

C থেকে একটি রুবি মেথড লেখা

আপনি C ফাংশন তৈরি করতে পারেন जिन्हें আপনি আপনার রুবি কোড থেকে কল করতে পারেন। বিল্ট-ইন ক্লাস এবং মেথডগুলো इसीভাবে কাজ করে।

সকল রুবি মেথড অবশ্যই একটি VALUE রিটার্ন করতে হবে। একটি VALUE হলো একটি রুবি অবজেক্ট।

উদাহরণ:

VALUE rb_return_nil() {
  return Qnil;
}

এখন আমাদের এই ফাংশনটি একটি রুবি ক্লাস বা মডিউলের সাথে আট্যাচ করতে হবে। আপনি একটি নতুন ক্লাস তৈরি করতে পারেন বা একটি বিদ্যমান ব্যবহার করতে পারেন।

এখানে আমি একটি মডিউল তৈরি করছি:

void Init_foobar() {
  VALUE mod = rb_define_module("RubyGuides");
  rb_define_method(mod, "return_nil", rb_return_nil, 0);
}

আপনি rb_define_method মেথড ব্যবহার করে C ফাংশনকে এই মডিউলের সাথে আট্যাচ করতে পারেন।

আর্গুমেন্টগুলো হলো:

আর্গুমেন্ট বিবরণ
mod মডিউল অবজেক্ট
"print_hello" রুবি মেথডের নাম
rb_print_hello C ফাংশনের নাম
0 এই মেথড কতটি আর্গুমেন্ট নেয়, ভেরিয়েবল আর্গুমেন্টের জন্য -1 ব্যবহার করুন

এখন আবার make রান করুন এক্সটেনশন কম্পাইল করতে, এবং এভাবে ট্রাই করুন:

require 'foobar'
include RubyGuides
print_hello

হয়ে গেলো, আপনি রুবি থেকে একটি C ফাংশন কল করলেন!

C থেকে একটি রুবি হ্যাশ তৈরি করা

প্রায়শই আপনি C থেকে রুবি অবজেক্ট তৈরি এবং ম্যানিপুলেট করতে চাবেন।

আপনি এটি C API ব্যবহার করে করতে পারেন।

উদাহরণস্বরূপ, একটি হ্যাশ তৈরি করা এবং কিছু এলিমেন্ট যোগ করা:

VALUE create_hash() {
  hash = rb_hash_new();
  rb_hash_aset(hash, rb_str_new2("test"), INT2FIX(1));
  return hash;
}

এখানে দুটি গুরুত্বপূর্ণ বিষয় লক্ষ্য করুন, প্রথমে rb_str_new2 ফাংশন, এটি একটি রুবি স্ট্রিং তৈরি করে।

তারপর INT2FIX ম্যাক্রো, এটি একটি রেগুলার ইন্টিজারকে রুবি ইন্টিজারে রূপান্তর করে।

এখন যদি আপনি এই ফাংশনকে রুবিতে এক্সপোজ করেন rb_define_method ব্যবহার করে তবে আপনি একটি রেগুলার রুবি হ্যাশ পাবেন একটা কী (test) এবং ভ্যালু 1 সহ।

প্রতিবার পরিবর্তন করার পর এক্সটেনশন রিকম্পাইল করা ভুলবেন না 🙂

স্ট্রিং এর সাথে কাজ করা

আপনার C ফাংশনগুলো প্যারামিটারও নিতে পারে।

উদাহরণস্বরূপ:

VALUE rb_print_length(VALUE self, VALUE str) {
  if (RB_TYPE_P(str, T_STRING) == 1) {
    return rb_sprintf("String length: %ld", RSTRING_LEN(str));
  }
  return Qnil;
}
void Init_foobar() {
  rb_define_global_function("print_length", rb_print_length, 1);
}

এখানে আমরা একটি VALUE (রুবি অবজেক্ট) আর্গুমেন্ট হিসেবে নিচ্ছি এবং তারপর RB_TYPE_P ম্যাক্রো দিয়ে নিশ্চিত করছি এটি একটি স্ট্রিং। তারপর, আমরা শুধু স্ট্রিং-এর দৈর্ঘ্য প্রিন্ট করছি RSTRING_LEN ম্যাক্রো ব্যবহার করে।

যদি আপনি স্ট্রিং ডেটার একটি পয়েন্টার চান তবে আপনি RSTRING_PTR ম্যাক্রো ব্যবহার করতে পারেন।

উদাহরণ:

VALUE rb_print_data(VALUE self, VALUE str) {
  if (RB_TYPE_P(str, T_STRING) == 1) {
    return rb_sprintf("String length: %s", RSTRING_LEN(str));
  }
  return Qnil;
}

এখানে আরেকটি প্যারামিটার আছে, self, এটি वो অবজেক্ট যেটি মেথড কল পাচ্ছে।

যদি আপনি এই মেথডটি String ক্লাসের ওপর সংজ্ঞায়িত করতে চান তবে আপনি এভাবে করবেন:

void Init_foobar() {
  rb_define_method(rb_cString, "print_length", rb_print_length, 0);
}

সারসংক্ষেপ

আপনি শিখতে পেরেছেন কীভাবে রুবির জন্য একটি C এক্সটেনশন লিখবেন যাতে আপনি আপনার রুবি প্রোগ্রাম থেকে C-এর সকল শক্তি অ্যাক্সেস করতে পারেন। আপনি শিখতে পেরেছেন কীভাবে C ফাংশনগুলো রুবিতে এক্সপোজ করবেন এবং কীভাবে C থেকে রুবি অবজেক্টের সাথে কাজ করবেন, যেমন স্ট্রিং এবং হ্যাশ।

আপনাকে যদি আরও ফাংশন দরকার হয় রুবির সাথে C থেকে ইন্টারঅ্যাক্ট করতে তবে আপনাকে সেগুলো রুবির সোর্স কোডে খুঁজে বের করতে হতে পারে এবং C এক্সটেনশন কোড পড়তে হবে যেহেতু এটি ভালোভাবে ডকুমেন্টেড নয়।

আশা করি আপনি এই আর্টিকেলটি উপকারী এবং আকর্ষণীয় পেয়েছেন! যদি হয় তবে আপনার বন্ধুদের সাথে শেয়ার করুন যাতে সégrা অনুভব করতে পারেন।

  1. রুবি ম্যাট্রিক্স বুঝতে: ডেফিনিশন, অ্যাপ্লিকেশন এবং কীভাবে তৈরি করবেন

  2. রুবি Struct ও OpenStruct: দক্ষ ভ্যালু অবজেক্টস

  3. রুবি পোর্ট স্ক্যানার তৈরি: নেটওয়ার্ক স্ক্যানিং-এর ধাপে ধাপে গাইড

  4. রুবিতে ফাইল পড়া এবং লেখা: একটি স্টেপ-বাই-স্টেপ গাইড