The problem of ruby load c dll. editor says :'unknown symbol'

I am new in ruby and c.when I try to code by the example show in the c sdk I have a problem when I want to load my dll.The dll is just compiled by vs studio2015.And I put the dll in the ruby’s search path. I just use ruby code editor and fiddle lib to load the dll. But the Ruby says unknown symbol ‘myfunction name’. who can help me. thanks a lot.

here is dll definition :

#include "stdafx.h"
#include "miniDll.h"

float Init_miniDll(float p1, float p2) {
	SUInitialize();
	SUModelRef model = SU_INVALID; 

	SUApplicationGetActiveModel(&model);


	SUEntitiesRef entities = SU_INVALID;
	SUModelGetEntities(model, &entities);

	SULoopInputRef outer_loop = SU_INVALID; 
	SULoopInputCreate(&outer_loop);
	for (size_t i = 0; i < 3; ++i)
	{
		SULoopInputAddVertexIndex(outer_loop, i);
	}

	SUFaceRef face = SU_INVALID; 
	SUPoint3D vertices[3] = { { p1, p2, p2 },{ p2, p2,p2 },{ p2, p2, p2 } };
	SUFaceCreate(&face, vertices, &outer_loop);
	SUEntitiesAddFaces(entities, 1, &face);
	return 0;
}

here is the h definition

#pragma once
#include <SketchUpAPI/geometry.h>
#include  <SketchUpAPI\model\edge.h>
#include <SketchUpAPI/slapi.h>
#include <SketchUpAPI/geometry.h>
#include <SketchUpAPI/initialize.h>
#include <SketchUpAPI/model/model.h>
#include <SketchUpAPI/model/entities.h>
#include <SketchUpAPI/model/face.h>
#include <SketchUpAPI/model/edge.h>
#include <SketchUpAPI/model/vertex.h>
#include <vector>
#include <SketchUpAPI\model\model.h>
#include <SketchUpAPI\application\application.h>

#ifdef DLLDEMO1_EXPORTS
#define EXPORTS_DEMO _declspec( dllexport )
extern "C" EXPORTS_DEMO  float Init_miniDll(float p1, float p2);
#endif

and here is Ruby code

require "fiddle"# Default 

libm=Fiddle.dlopen('C:/Users/Administrator/Documents/Visual Studio 2015/Projects/miniDll/x64/Debug/miniDll.dll')

test1=Fiddle::Function.new(libm['Init_miniDll'], [Fiddle::TYPE_FLOAT]*2,Fiddle::TYPE_FLOAT]

(1) Please edit your previous post and properly delimit code blocks for forum posting.

… and please do not post images of code. Cut and paste the code into a delimited code block.


(2) You cannot use the C API to change a live model at this time. You can only read stuff from the model, say for creating an exporter, or building another model file that is not the active model.

The C API was written for 3rd party applications to create importers and exporters for their applications.


(3) You did not properly terminate your code’s use of the API interface.
Please reread the “Quick Start” on this introductory page …
https://extensions.sketchup.com/developers/sketchup_c_api/sketchup/index.html

  // Must release the model or there will be memory leaks
  SUModelRelease(&model);
  // Always terminate the API when done using it
  SUTerminate();
  return 0;

(4) You do not need Fiddle to load a Ruby C extension if you’ve properly defined a Ruby entry point function … ie "Init_SameNameAsDLLfile"

You just use the global require() defined in the Kernel module (which is mixed into Object making it global.) … from the doc for this method (with emphasis by me)

If the filename has the extension “.rb”, it is loaded as a source file; if the extension is “.so”, “.o”, or “.dll”, or the default shared library extension on the current platform, Ruby loads the shared library as a Ruby extension.


(5) The entry point function should define Ruby object to access C functionality. Ie, it should create your module objects (your toplevel namespace module, and it’s extension specific submodule,) and within those define Ruby methods that when called in Ruby, fire off C or C++ functions.


(6) Then please first learn how the SketchUp API works using Ruby scripting. Creating C Ruby extensions is very advanced.

thanks a lot 。but I still want to know how to use fiddle to call c dll. I modify the code .try to using ruby to call ''test ‘’ which is not entry point function.but still can’t get it. could you please tell me the reason. the editor still tell me that ‘unknown symbl’.
the h file

#pragma once
#include <SketchUpAPI/geometry.h>
#include  <SketchUpAPI\model\edge.h>
#include <SketchUpAPI/slapi.h>
#include <SketchUpAPI/geometry.h>
#include <SketchUpAPI/initialize.h>
#include <SketchUpAPI/model/model.h>
#include <SketchUpAPI/model/entities.h>
#include <SketchUpAPI/model/face.h>
#include <SketchUpAPI/model/edge.h>
#include <SketchUpAPI/model/vertex.h>
#include <vector>
#include <SketchUpAPI\model\model.h>
#include <SketchUpAPI\application\application.h>

#ifdef DLLDEMO1_EXPORTS
#define EXPORTS_DEMO _declspec( dllexport )
extern "C" EXPORTS_DEMO  float test(float p1, float p2);
#endif

The dll file

#include "stdafx.h"
#include "miniDll.h"

float test(float p1, float p2) {
	SUInitialize();
	SUModelRef model = SU_INVALID; 

	SUApplicationGetActiveModel(&model);


	SUEntitiesRef entities = SU_INVALID;
	SUModelGetEntities(model, &entities);

	SULoopInputRef outer_loop = SU_INVALID; 
	SULoopInputCreate(&outer_loop);
	for (size_t i = 0; i < 3; ++i)
	{
		SULoopInputAddVertexIndex(outer_loop, i);
	}

	SUFaceRef face = SU_INVALID; 
	SUPoint3D vertices[3] = { { p1, p2, p2 },{ p2, p2,p2 },{ p2, p2, p2 } };
	SUFaceCreate(&face, vertices, &outer_loop);
	SUEntitiesAddFaces(entities, 1, &face);
	return 0;
}

the ruby file

require "fiddle"# Default code, use or delete...

libm=Fiddle.dlopen('C:/Users/Administrator/Documents/Visual Studio 2015/Projects/miniDll/x64/Debug/miniDll.dll')

test1=Fiddle::Function.new(libm['test'], [Fiddle::TYPE_FLOAT]*2,Fiddle::TYPE_FLOAT)

the reason I didn’t add SUModelRelease and SUTerminate is that I just call the active model to add some thing. when the function end. the model still exist.

Use the Fiddle::Importer mixin module …
https://ruby-doc.org/stdlib-2.5.5/libdoc/fiddle/rdoc/Fiddle/Importer.html

Well then enjoy your memory leaks!

well I copy the marco from
the internet to the h file. and load dll successfully. thanks. but it’s true that the geometry didn’t appear in the scence…meaning. I can’t create geometry in the active_model through c sdk. why you inventors make the limitation. why you don’t let the other developers interactive with sketchup through c.

the c file


#ifndef _MYCODE_H_
#define _MYCODE_H_
#ifdef DLLDEMO1_EXPORTS
#define EXPORTS_DEMO _declspec( dllexport )
#else
#define EXPORTS_DEMO _declspec(dllimport)
#endif
extern "C" EXPORTS_DEMO  float test(float p1, float p2, float p3, float p4, float p5, float p6, float p7, float p8, float p9);
extern "C" EXPORTS_DEMO int add(int a, int b);
#endif


The C API is an overhaul of the old C++ SDK, which was always for 3rd party applications operating upon files.

And I do not work for Trimble SketchUp.

It has been already requested and is on the list of things to do.

@tt_su, anything to add ?

Well, you may be able to create geometry, but you’ll likely destabilize the application and could corrupt the model data.

Your main problem is that a face must have a minimum of 3 non-coincident vertices.
(Your code uses the same struct for vertices[1] and vertices[2].)

Also the face should be planar.


oh yeah. it works :smile:
forgive my careless mistake

There you go posting images of code again :roll_eyes: :laughing:

Just so you know the Ruby API #add_face method will also fail silently if you pass invalid point arguments.

In your bad code, you never got the result from calling the SUFaceCreate function. There are 6 error return values that can tell you what went wrong.

You could have returned the error code instead of just 0. :wink:

no no no it works,:smiley:,The return value is 0 and I have got the triangle in the active model.Thanks for your help again!

I meant when you were doing it wrong. If you check the result codes, they tell you when things go wrong.

en,I get it。thanks。

1 Like