TensorFlow DLL for Windows (64 bits)

Re: TensorFlow DLL for Windows (64 bits)

Postby Antonio Linares » Tue Jun 06, 2017 11:29 am

More recent version. We are not receiving in the hTensorOutput the expected output yet (the type is fine, but not the contents of the string)

tf.prg
Code: Select all  Expand view
#include "FiveWin.ch"

#define TF_STRING  6

static hDLL

function Main()

   local oTF := TensorFlow():New()
   local hTensor, hOperationDescription, hOperation
   local hTensorOutput := 0

   MsgInfo( oTF:Version() )

   hTensor = oTF:TensorString( "Hello TensorFlow" )
   hOperationDescription = TF_NewOperation( oTF:hGraph, "Const", "hello" )
   TF_SetAttrTensor( hOperationDescription, "value", hTensor, oTF:hStatus )
   TF_SetAttrType( hOperationDescription, "dtype", TF_TensorType( hTensor ) )
   hOperation = TF_FinishOperation( hOperationDescription, oTF:hStatus )

   TF_SessionRun( oTF:hSession, 0,;
                  0, 0, 0,;  // Inputs    
                  TF_Output( hOperation, 0 ), @hTensorOutput, 1,;  // Outputs
                  hOperation, 1,;  // Operations
                  0, oTF:hStatus )

   MsgInfo( oTF:StatusCode(), "zero means ok" )

   MsgInfo( TF_TensorType( hTensorOutput ) )
   MsgInfo( L2Str( TF_TensorData( hTensorOutput ) ) )

   oTF:End()

return nil

CLASS TensorFlow

   DATA hGraph
   DATA hOptions
   DATA hStatus
   DATA hSession

   METHOD New()
   
   METHOD Version() INLINE TF_Version()

   METHOD ImportGraph( cFileName )

   METHOD TensorString( cString )

   METHOD End()
   
   METHOD StatusCode() INLINE TF_GetCode( ::hStatus )

   METHOD Variable( cVarName, nDataType )

ENDCLASS

METHOD New() CLASS TensorFlow

   hDLL = LoadLibrary( "tensorflow.dll" )

   ::hGraph = TF_NewGraph()
   ::hOptions = TF_NewSessionOptions()
   ::hStatus = TF_NewStatus()
   ::hSession = TF_NewSession( ::hGraph, ::hOptions, ::hStatus )
     
return Self    

METHOD End() CLASS TensorFlow

   TF_CloseSession( ::hSession, ::hStatus )
   TF_DeleteSession( ::hSession, ::hStatus )
   TF_DeleteStatus( ::hStatus )
   TF_DeleteSessionOptions( ::hOptions )

   FreeLibrary( hDLL )

return nil

METHOD ImportGraph( cFileName ) CLASS TensorFlow

   local cGraph := MemoRead( cFileName )
   local hGraphDefOptions := TF_NewImportGraphDefOptions()
   
   TF_GraphImportGraphDef( ::hGraph, TF_NewBufferFromString( cGraph, Len( cGraph ) ), hGraphDefOptions, ::hStatus )
   
   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error importing a Graph file" )
   endif
   
   TF_DeleteImportGraphDefOptions( hGraphDefOptions )
   
return nil  

METHOD TensorString( cString ) CLASS TensorFlow

   local hTensor := TF_AllocateTensor( TF_STRING, 0, 0, 8 + TF_StringEncodedSize( Len( cString ) ) )
   
   Memset( TF_TensorData( hTensor ), 0, 8 )
   
   TF_StringEncode( cString, Len( cString ), 8 + TF_TensorData( hTensor ), TF_StringEncodedSize( Len( cString ) ), ::hStatus )

   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error creating a Tensor string" )
   endif
   
return hTensor  

METHOD Variable( cVarName, nDataType ) CLASS TensorFlow

   local hOperationDescription := TF_NewOperation( ::hGraph, "Variable", cVarName )

   TF_SetAttrType( hOperationDescription, "dtype", nDataType )

return TF_FinishOperation( hOperationDescription, ::hStatus )

DLL FUNCTION TF_Version() AS LPSTR LIB hDLL

DLL FUNCTION TF_NewGraph() AS LONG LIB hDLL

DLL FUNCTION TF_NewSessionOptions() AS LONG LIB hDLL

DLL FUNCTION TF_NewStatus() AS LONG LIB hDLL

DLL FUNCTION TF_NewSession( hGraph AS LONG, hOptions AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_CloseSession( hSession AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteSession( hSession AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteStatus( hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteSessionOptions( hOptions AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_NewImportGraphDefOptions() AS LONG LIB hDLL

DLL FUNCTION TF_GraphImportGraphDef( hGraph AS LONG, hBuffer AS LONG, hGraphDefOptions AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_NewBufferFromString( cString AS LPSTR, nLegth AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_GetCode( hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_DeleteImportGraphDefOptions( hGraphDefOptions AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_NewTensor( nType AS LONG, pDims AS LONG, nDims AS LONG, pData AS LONG, nLength AS LONG, pDeallocator AS LONG,;
                           pDeallocatorArgs AS LONG ) AS LONG LIB hDLL
                           
DLL FUNCTION TF_AllocateTensor( nType AS LONG, pDims AS LONG, nDims AS LONG, nLegth AS LONG ) AS LONG LIB hDLL
                           
DLL FUNCTION TF_StringEncodedSize( nLength AS LONG ) AS LONG LIB hDLL    

DLL FUNCTION TF_TensorData( hTensor AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_StringEncode( cString AS LPSTR, nLength AS LONG, pDest AS LONG, nDestLength AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_SessionRun( hSession AS LONG, hRunOptions AS LONG, hInputs AS LONG, @hInputValues AS LONG, nInputs AS LONG,;
                            hOutputs AS LONG, @hOutputValues AS LONG, nOutputs AS LONG, @hTargetOperations AS LONG, nTargets AS LONG,;
                            hRunMetadata AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_Message( hStatus AS LONG ) AS LPSTR LIB hDLL

DLL FUNCTION TF_NewOperation( hGraph AS LONG, cOperationType AS LPSTR, cOperationName AS LPSTR ) AS LONG LIB hDLL

DLL FUNCTION TF_SetAttrTensor( hOperationDescription AS LONG, cAttributeName AS LPSTR, hTensor AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_TensorType( hTensor AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_SetAttrType( hOperationDescription AS LONG, cAttributeName AS LPSTR, nDataType AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_FinishOperation( hOperationDescription AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

#pragma BEGINDUMP

#include <hbapi.h>

typedef struct TF_Output {
  void * oper;
  int index;
} TF_Output;

HB_FUNC( TF_OUTPUT )
{
   TF_Output * hOutput = ( TF_Output * ) hb_xgrab( sizeof( TF_Output ) );
   
   hOutput->oper = ( void * ) hb_parnll( 1 );
   hOutput->index = hb_parnl( 2 );
   
   hb_retnll( ( HB_LONGLONG ) hOutput );
}  

HB_FUNC( L2STR )
{
   hb_retc( ( ( char * ) hb_parnll( 1 ) ) + 9 );
}  

HB_FUNC( MEMSET )
{
   hb_retnll( ( HB_LONGLONG ) memset( ( void * ) hb_parnll( 1 ), hb_parnl( 2 ), hb_parnll( 3 ) ) );
}  

#pragma ENDDUMP
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Antonio Linares
Site Admin
 
Posts: 41289
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain

Re: TensorFlow DLL for Windows (64 bits)

Postby Antonio Linares » Tue Jun 06, 2017 10:22 pm

We keep enhancing the Class TensorFlow, so our code gets simpler:

still there is a bug retrieving the output string. Using C++ is working fine.

tf.prg
Code: Select all  Expand view
#include "FiveWin.ch"

#define TF_STRING  6

static hDLL

function Main()

   local oTF := TensorFlow():New()
   local hOperation := oTF:Constant( "hello TensorFlow!", "hello" )
   local hTensorOutput := 0

   MsgInfo( oTF:Version() )

   TF_SessionRun( oTF:hSession, 0,;
                  0, 0, 0,;  // Inputs    
                  TF_Output( hOperation, 0 ), @hTensorOutput, 1,;  // Outputs
                  hOperation, 1,;  // Operations
                  0, oTF:hStatus )

   MsgInfo( oTF:StatusCode(), "zero means ok" )

   MsgInfo( TF_TensorType( hTensorOutput ) )
   MsgInfo( TF_TensorString( TF_TensorData( hTensorOutput ) ) )

   oTF:End()

return nil

CLASS TensorFlow

   DATA hGraph
   DATA hOptions
   DATA hStatus
   DATA hSession

   METHOD New()
   
   METHOD Version() INLINE TF_Version()

   METHOD ImportGraph( cFileName )

   METHOD TensorString( cString )

   METHOD End()
   
   METHOD StatusCode() INLINE TF_GetCode( ::hStatus )

   METHOD Variable( cVarName, nDataType )

   METHOD Constant( uValue, cName )

ENDCLASS

METHOD New() CLASS TensorFlow

   hDLL = LoadLibrary( "tensorflow.dll" )

   ::hGraph = TF_NewGraph()
   ::hOptions = TF_NewSessionOptions()
   ::hStatus = TF_NewStatus()
   ::hSession = TF_NewSession( ::hGraph, ::hOptions, ::hStatus )
     
return Self    

METHOD End() CLASS TensorFlow

   TF_CloseSession( ::hSession, ::hStatus )
   TF_DeleteSession( ::hSession, ::hStatus )
   TF_DeleteStatus( ::hStatus )
   TF_DeleteSessionOptions( ::hOptions )

   FreeLibrary( hDLL )

return nil

METHOD ImportGraph( cFileName ) CLASS TensorFlow

   local cGraph := MemoRead( cFileName )
   local hGraphDefOptions := TF_NewImportGraphDefOptions()
   
   TF_GraphImportGraphDef( ::hGraph, TF_NewBufferFromString( cGraph, Len( cGraph ) ), hGraphDefOptions, ::hStatus )
   
   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error importing a Graph file" )
   endif
   
   TF_DeleteImportGraphDefOptions( hGraphDefOptions )
   
return nil  

METHOD TensorString( cString ) CLASS TensorFlow

   local hTensor := TF_AllocateTensor( TF_STRING, 0, 0, 8 + TF_StringEncodedSize( Len( cString ) ) )
   
   Memset( TF_TensorData( hTensor ), 0, 8 )
   
   TF_StringEncode( cString, Len( cString ), 8 + TF_TensorData( hTensor ), TF_StringEncodedSize( Len( cString ) ), ::hStatus )

   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error creating a Tensor string" )
   endif
   
return hTensor  

METHOD Variable( cVarName, nDataType ) CLASS TensorFlow

   local hOperationDescription := TF_NewOperation( ::hGraph, "Variable", cVarName )

   TF_SetAttrType( hOperationDescription, "dtype", nDataType )

return TF_FinishOperation( hOperationDescription, ::hStatus )

METHOD Constant( uValue, cName ) CLASS TensorFlow

   local hOperationDescription, hTensor
   
   do case
      case ValType( uValue ) == "C"
         hTensor = ::TensorString( uValue )
         hOperationDescription = TF_NewOperation( ::hGraph, "Const", cName )
         TF_SetAttrTensor( hOperationDescription, "value", hTensor, ::hStatus )
         TF_SetAttrType( hOperationDescription, "dtype", TF_TensorType( hTensor ) )
   endcase

return TF_FinishOperation( hOperationDescription, ::hStatus )

DLL FUNCTION TF_Version() AS LPSTR LIB hDLL

DLL FUNCTION TF_NewGraph() AS LONG LIB hDLL

DLL FUNCTION TF_NewSessionOptions() AS LONG LIB hDLL

DLL FUNCTION TF_NewStatus() AS LONG LIB hDLL

DLL FUNCTION TF_NewSession( hGraph AS LONG, hOptions AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_CloseSession( hSession AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteSession( hSession AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteStatus( hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteSessionOptions( hOptions AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_NewImportGraphDefOptions() AS LONG LIB hDLL

DLL FUNCTION TF_GraphImportGraphDef( hGraph AS LONG, hBuffer AS LONG, hGraphDefOptions AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_NewBufferFromString( cString AS LPSTR, nLegth AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_GetCode( hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_DeleteImportGraphDefOptions( hGraphDefOptions AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_NewTensor( nType AS LONG, pDims AS LONG, nDims AS LONG, pData AS LONG, nLength AS LONG, pDeallocator AS LONG,;
                           pDeallocatorArgs AS LONG ) AS LONG LIB hDLL
                           
DLL FUNCTION TF_AllocateTensor( nType AS LONG, pDims AS LONG, nDims AS LONG, nLegth AS LONG ) AS LONG LIB hDLL
                           
DLL FUNCTION TF_StringEncodedSize( nLength AS LONG ) AS LONG LIB hDLL    

DLL FUNCTION TF_TensorData( hTensor AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_StringEncode( cString AS LPSTR, nLength AS LONG, pDest AS LONG, nDestLength AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_SessionRun( hSession AS LONG, hRunOptions AS LONG, hInputs AS LONG, @hInputValues AS LONG, nInputs AS LONG,;
                            hOutputs AS LONG, @hOutputValues AS LONG, nOutputs AS LONG, @hTargetOperations AS LONG, nTargets AS LONG,;
                            hRunMetadata AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_Message( hStatus AS LONG ) AS LPSTR LIB hDLL

DLL FUNCTION TF_NewOperation( hGraph AS LONG, cOperationType AS LPSTR, cOperationName AS LPSTR ) AS LONG LIB hDLL

DLL FUNCTION TF_SetAttrTensor( hOperationDescription AS LONG, cAttributeName AS LPSTR, hTensor AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_TensorType( hTensor AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_SetAttrType( hOperationDescription AS LONG, cAttributeName AS LPSTR, nDataType AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_FinishOperation( hOperationDescription AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

#pragma BEGINDUMP

#include <hbapi.h>

typedef struct TF_Output {
  void * oper;
  int index;
} TF_Output;

HB_FUNC( TF_OUTPUT )
{
   TF_Output * hOutput = ( TF_Output * ) hb_xgrab( sizeof( TF_Output ) );
   
   hOutput->oper = ( void * ) hb_parnll( 1 );
   hOutput->index = hb_parnl( 2 );
   
   hb_retnll( ( HB_LONGLONG ) hOutput );
}  

HB_FUNC( TF_TENSORSTRING )
{
   hb_retc( ( ( char * ) hb_parnll( 1 ) ) + 8 );
}  

HB_FUNC( MEMSET )
{
   hb_retnll( ( HB_LONGLONG ) memset( ( void * ) hb_parnll( 1 ), hb_parnl( 2 ), hb_parnll( 3 ) ) );
}  

#pragma ENDDUMP
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Antonio Linares
Site Admin
 
Posts: 41289
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain

Re: TensorFlow DLL for Windows (64 bits)

Postby Antonio Linares » Tue Jun 06, 2017 10:34 pm

Simpler code:

tf.prg
Code: Select all  Expand view
#include "FiveWin.ch"

#define TF_STRING  6

static hDLL

function Main()

   local oTF := TensorFlow():New()
   local hOperation := oTF:Constant( "hello TensorFlow!", "hello" )
   local hTensorOutput

   MsgInfo( oTF:Version() )

   hTensorOutput = oTF:Run( hOperation )
   MsgInfo( oTF:StatusCode(), "zero means ok" )

   MsgInfo( TF_TensorType( hTensorOutput ) )
   MsgInfo( TF_TensorString( TF_TensorData( hTensorOutput ) ) )

   oTF:End()

return nil

CLASS TensorFlow

   DATA hGraph
   DATA hOptions
   DATA hStatus
   DATA hSession

   METHOD New()
   
   METHOD Version() INLINE TF_Version()

   METHOD ImportGraph( cFileName )

   METHOD TensorString( cString )

   METHOD End()
   
   METHOD StatusCode() INLINE TF_GetCode( ::hStatus )

   METHOD Variable( cVarName, nDataType )

   METHOD Constant( uValue, cName )

   METHOD Run( hOperation )

ENDCLASS

METHOD New() CLASS TensorFlow

   hDLL = LoadLibrary( "tensorflow.dll" )

   ::hGraph = TF_NewGraph()
   ::hOptions = TF_NewSessionOptions()
   ::hStatus = TF_NewStatus()
   ::hSession = TF_NewSession( ::hGraph, ::hOptions, ::hStatus )
     
return Self    

METHOD End() CLASS TensorFlow

   TF_CloseSession( ::hSession, ::hStatus )
   TF_DeleteSession( ::hSession, ::hStatus )
   TF_DeleteStatus( ::hStatus )
   TF_DeleteSessionOptions( ::hOptions )

   FreeLibrary( hDLL )

return nil

METHOD ImportGraph( cFileName ) CLASS TensorFlow

   local cGraph := MemoRead( cFileName )
   local hGraphDefOptions := TF_NewImportGraphDefOptions()
   
   TF_GraphImportGraphDef( ::hGraph, TF_NewBufferFromString( cGraph, Len( cGraph ) ), hGraphDefOptions, ::hStatus )
   
   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error importing a Graph file" )
   endif
   
   TF_DeleteImportGraphDefOptions( hGraphDefOptions )
   
return nil  

METHOD TensorString( cString ) CLASS TensorFlow

   local hTensor := TF_AllocateTensor( TF_STRING, 0, 0, 8 + TF_StringEncodedSize( Len( cString ) ) )
   
   Memset( TF_TensorData( hTensor ), 0, 8 )
   
   TF_StringEncode( cString, Len( cString ), 8 + TF_TensorData( hTensor ), TF_StringEncodedSize( Len( cString ) ), ::hStatus )

   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error creating a Tensor string" )
   endif
   
return hTensor  

METHOD Variable( cVarName, nDataType ) CLASS TensorFlow

   local hOperationDescription := TF_NewOperation( ::hGraph, "Variable", cVarName )

   TF_SetAttrType( hOperationDescription, "dtype", nDataType )

return TF_FinishOperation( hOperationDescription, ::hStatus )

METHOD Constant( uValue, cName ) CLASS TensorFlow

   local hOperationDescription, hTensor
   
   do case
      case ValType( uValue ) == "C"
         hTensor = ::TensorString( uValue )
         hOperationDescription = TF_NewOperation( ::hGraph, "Const", cName )
         TF_SetAttrTensor( hOperationDescription, "value", hTensor, ::hStatus )
         TF_SetAttrType( hOperationDescription, "dtype", TF_TensorType( hTensor ) )
   endcase

return TF_FinishOperation( hOperationDescription, ::hStatus )

METHOD Run( hOperation ) CLASS TensorFlow

   local hTensorOutput := 0

   TF_SessionRun( ::hSession, 0,;
                  0, 0, 0,;  // Inputs    
                  TF_Output( hOperation, 0 ), @hTensorOutput, 1,;  // Outputs
                  hOperation, 1,;  // Operations
                  0, ::hStatus )

return hTensorOutput

DLL FUNCTION TF_Version() AS LPSTR LIB hDLL

DLL FUNCTION TF_NewGraph() AS LONG LIB hDLL

DLL FUNCTION TF_NewSessionOptions() AS LONG LIB hDLL

DLL FUNCTION TF_NewStatus() AS LONG LIB hDLL

DLL FUNCTION TF_NewSession( hGraph AS LONG, hOptions AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_CloseSession( hSession AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteSession( hSession AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteStatus( hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteSessionOptions( hOptions AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_NewImportGraphDefOptions() AS LONG LIB hDLL

DLL FUNCTION TF_GraphImportGraphDef( hGraph AS LONG, hBuffer AS LONG, hGraphDefOptions AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_NewBufferFromString( cString AS LPSTR, nLegth AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_GetCode( hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_DeleteImportGraphDefOptions( hGraphDefOptions AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_NewTensor( nType AS LONG, pDims AS LONG, nDims AS LONG, pData AS LONG, nLength AS LONG, pDeallocator AS LONG,;
                           pDeallocatorArgs AS LONG ) AS LONG LIB hDLL
                           
DLL FUNCTION TF_AllocateTensor( nType AS LONG, pDims AS LONG, nDims AS LONG, nLegth AS LONG ) AS LONG LIB hDLL
                           
DLL FUNCTION TF_StringEncodedSize( nLength AS LONG ) AS LONG LIB hDLL    

DLL FUNCTION TF_TensorData( hTensor AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_StringEncode( cString AS LPSTR, nLength AS LONG, pDest AS LONG, nDestLength AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_SessionRun( hSession AS LONG, hRunOptions AS LONG, hInputs AS LONG, @hInputValues AS LONG, nInputs AS LONG,;
                            hOutputs AS LONG, @hOutputValues AS LONG, nOutputs AS LONG, @hTargetOperations AS LONG, nTargets AS LONG,;
                            hRunMetadata AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_Message( hStatus AS LONG ) AS LPSTR LIB hDLL

DLL FUNCTION TF_NewOperation( hGraph AS LONG, cOperationType AS LPSTR, cOperationName AS LPSTR ) AS LONG LIB hDLL

DLL FUNCTION TF_SetAttrTensor( hOperationDescription AS LONG, cAttributeName AS LPSTR, hTensor AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_TensorType( hTensor AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_SetAttrType( hOperationDescription AS LONG, cAttributeName AS LPSTR, nDataType AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_FinishOperation( hOperationDescription AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

#pragma BEGINDUMP

#include <hbapi.h>

typedef struct TF_Output {
  void * oper;
  int index;
} TF_Output;

HB_FUNC( TF_OUTPUT )
{
   TF_Output * hOutput = ( TF_Output * ) hb_xgrab( sizeof( TF_Output ) );
   
   hOutput->oper = ( void * ) hb_parnll( 1 );
   hOutput->index = hb_parnl( 2 );
   
   hb_retnll( ( HB_LONGLONG ) hOutput );
}  

HB_FUNC( TF_TENSORSTRING )
{
   hb_retc( ( ( char * ) hb_parnll( 1 ) ) + 8 );
}  

HB_FUNC( MEMSET )
{
   hb_retnll( ( HB_LONGLONG ) memset( ( void * ) hb_parnll( 1 ), hb_parnl( 2 ), hb_parnll( 3 ) ) );
}  

#pragma ENDDUMP
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Antonio Linares
Site Admin
 
Posts: 41289
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain

Re: TensorFlow DLL for Windows (64 bits)

Postby Antonio Linares » Wed Jun 07, 2017 5:44 am

Bug fixed and finally it is working fine! :-)

tf.prg
Code: Select all  Expand view
#include "FiveWin.ch"

#define TF_STRING  7

static hDLL

function Main()

   local oTF := TensorFlow():New()
   local hOperation := oTF:Constant( "hello TensorFlow!", "hello" )
   local hTensorOutput

   MsgInfo( oTF:Version() )

   hTensorOutput = oTF:Run( hOperation )
   MsgInfo( oTF:StatusCode(), "zero means ok" )

   MsgInfo( TF_TensorType( hTensorOutput ) )
   MsgInfo( TF_TensorString( TF_TensorData( hTensorOutput ) ) )

   oTF:End()

return nil

CLASS TensorFlow

   DATA hGraph
   DATA hOptions
   DATA hStatus
   DATA hSession

   METHOD New()
   
   METHOD Version() INLINE TF_Version()

   METHOD ImportGraph( cFileName )

   METHOD TensorNum( nValue )

   METHOD TensorString( cString )

   METHOD End()
   
   METHOD StatusCode() INLINE TF_GetCode( ::hStatus )

   METHOD Variable( cVarName, nDataType )

   METHOD Constant( uValue, cName )

   METHOD Run( hOperation )

ENDCLASS

METHOD New() CLASS TensorFlow

   hDLL = LoadLibrary( "tensorflow.dll" )

   ::hGraph = TF_NewGraph()
   ::hOptions = TF_NewSessionOptions()
   ::hStatus = TF_NewStatus()
   ::hSession = TF_NewSession( ::hGraph, ::hOptions, ::hStatus )
     
return Self    

METHOD End() CLASS TensorFlow

   TF_CloseSession( ::hSession, ::hStatus )
   TF_DeleteSession( ::hSession, ::hStatus )
   TF_DeleteStatus( ::hStatus )
   TF_DeleteSessionOptions( ::hOptions )

   FreeLibrary( hDLL )

return nil

METHOD ImportGraph( cFileName ) CLASS TensorFlow

   local cGraph := MemoRead( cFileName )
   local hGraphDefOptions := TF_NewImportGraphDefOptions()
   
   TF_GraphImportGraphDef( ::hGraph, TF_NewBufferFromString( cGraph, Len( cGraph ) ), hGraphDefOptions, ::hStatus )
   
   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error importing a Graph file" )
   endif
   
   TF_DeleteImportGraphDefOptions( hGraphDefOptions )
   
return nil  

METHOD TensorNum( nValue ) CLASS TensorFlow

   local hTensor := TF_NewTensor( TF_INT32, 0, 0, @nValue, 4, 0, 0 )
   
return hTensor

METHOD TensorString( cString ) CLASS TensorFlow

   local hTensor := TF_AllocateTensor( TF_STRING, 0, 0, 8 + TF_StringEncodedSize( Len( cString ) ) )
   
   Memset( TF_TensorData( hTensor ), 0, 8 )
   
   TF_StringEncode( cString, Len( cString ), 8 + TF_TensorData( hTensor ), TF_StringEncodedSize( Len( cString ) ), ::hStatus )

   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error creating a Tensor string" )
   endif
   
return hTensor  

METHOD Variable( cVarName, nDataType ) CLASS TensorFlow

   local hOperationDescription := TF_NewOperation( ::hGraph, "Variable", cVarName )

   TF_SetAttrType( hOperationDescription, "dtype", nDataType )

return TF_FinishOperation( hOperationDescription, ::hStatus )

METHOD Constant( uValue, cName ) CLASS TensorFlow

   local hOperationDescription, hTensor
   
   do case
      case ValType( uValue ) == "C"
         hTensor = ::TensorString( uValue )
         
      case ValType( uValue ) == "N"
         hTensor = ::TensorNum( uValue )
   endcase

   hOperationDescription = TF_NewOperation( ::hGraph, "Const", cName )
   TF_SetAttrTensor( hOperationDescription, "value", hTensor, ::hStatus )
   TF_SetAttrType( hOperationDescription, "dtype", TF_TensorType( hTensor ) )

return TF_FinishOperation( hOperationDescription, ::hStatus )

METHOD Run( hOperation ) CLASS TensorFlow

   local hTensorOutput := 0

   TF_SessionRun( ::hSession, 0,;
                  0, 0, 0,;  // Inputs    
                  TF_Output( hOperation, 0 ), @hTensorOutput, 1,;  // Outputs
                  hOperation, 1,;  // Operations
                  0, ::hStatus )

return hTensorOutput

DLL FUNCTION TF_Version() AS LPSTR LIB hDLL

DLL FUNCTION TF_NewGraph() AS LONG LIB hDLL

DLL FUNCTION TF_NewSessionOptions() AS LONG LIB hDLL

DLL FUNCTION TF_NewStatus() AS LONG LIB hDLL

DLL FUNCTION TF_NewSession( hGraph AS LONG, hOptions AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_CloseSession( hSession AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteSession( hSession AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteStatus( hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteSessionOptions( hOptions AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_NewImportGraphDefOptions() AS LONG LIB hDLL

DLL FUNCTION TF_GraphImportGraphDef( hGraph AS LONG, hBuffer AS LONG, hGraphDefOptions AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_NewBufferFromString( cString AS LPSTR, nLegth AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_GetCode( hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_DeleteImportGraphDefOptions( hGraphDefOptions AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_NewTensor( nType AS LONG, pDims AS LONG, nDims AS LONG, pData AS LONG, nLength AS LONG, pDeallocator AS LONG,;
                           pDeallocatorArgs AS LONG ) AS LONG LIB hDLL
                           
DLL FUNCTION TF_AllocateTensor( nType AS LONG, pDims AS LONG, nDims AS LONG, nLegth AS LONG ) AS LONG LIB hDLL
                           
DLL FUNCTION TF_StringEncodedSize( nLength AS LONG ) AS LONG LIB hDLL    

DLL FUNCTION TF_TensorData( hTensor AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_StringEncode( cString AS LPSTR, nLength AS LONG, pDest AS LONG, nDestLength AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_SessionRun( hSession AS LONG, hRunOptions AS LONG, hInputs AS LONG, @hInputValues AS LONG, nInputs AS LONG,;
                            hOutputs AS LONG, @hOutputValues AS LONG, nOutputs AS LONG, @hTargetOperations AS LONG, nTargets AS LONG,;
                            hRunMetadata AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_Message( hStatus AS LONG ) AS LPSTR LIB hDLL

DLL FUNCTION TF_NewOperation( hGraph AS LONG, cOperationType AS LPSTR, cOperationName AS LPSTR ) AS LONG LIB hDLL

DLL FUNCTION TF_SetAttrTensor( hOperationDescription AS LONG, cAttributeName AS LPSTR, hTensor AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_TensorType( hTensor AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_SetAttrType( hOperationDescription AS LONG, cAttributeName AS LPSTR, nDataType AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_FinishOperation( hOperationDescription AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

#pragma BEGINDUMP

#include <hbapi.h>

typedef struct TF_Output {
  void * oper;
  int index;
} TF_Output;

HB_FUNC( TF_OUTPUT )
{
   TF_Output * hOutput = ( TF_Output * ) hb_xgrab( sizeof( TF_Output ) );
   
   hOutput->oper = ( void * ) hb_parnll( 1 );
   hOutput->index = hb_parnl( 2 );
   
   hb_retnll( ( HB_LONGLONG ) hOutput );
}  

HB_FUNC( TF_TENSORSTRING )
{
   hb_retc( ( ( char * ) hb_parnll( 1 ) ) + 9 );
}  

HB_FUNC( MEMSET )
{
   hb_retnll( ( HB_LONGLONG ) memset( ( void * ) hb_parnll( 1 ), hb_parnl( 2 ), hb_parnll( 3 ) ) );
}  

#pragma ENDDUMP


Image
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Antonio Linares
Site Admin
 
Posts: 41289
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain

Re: TensorFlow DLL for Windows (64 bits)

Postby Antonio Linares » Wed Jun 07, 2017 6:20 am

Simpler code and easier to understand it :-)

tf.prg
Code: Select all  Expand view
#include "FiveWin.ch"

#define TF_INT32   3
#define TF_STRING  7

static hDLL

function Main()

   local oTF := TensorFlow():New()

   MsgInfo( oTF:Version() )

   oTF:Run( oTF:Constant( "Hello TensorFlow!", "hello" ) )

   MsgInfo( oTF:Output() )

   oTF:End()

return nil

CLASS TensorFlow

   DATA hGraph
   DATA hOptions
   DATA hStatus
   DATA hSession
   DATA hTensorOutput

   METHOD New()
   
   METHOD Version() INLINE TF_Version()

   METHOD ImportGraph( cFileName )

   METHOD TensorNum( nValue )

   METHOD TensorString( cString )

   METHOD End()
   
   METHOD StatusCode() INLINE TF_GetCode( ::hStatus )

   METHOD Variable( cVarName, nDataType )

   METHOD Constant( uValue, cName )

   METHOD Run( hOperation )

   METHOD Output()

ENDCLASS

METHOD New() CLASS TensorFlow

   hDLL = LoadLibrary( "tensorflow.dll" )

   ::hGraph = TF_NewGraph()
   ::hOptions = TF_NewSessionOptions()
   ::hStatus = TF_NewStatus()
   ::hSession = TF_NewSession( ::hGraph, ::hOptions, ::hStatus )
     
return Self    

METHOD End() CLASS TensorFlow

   TF_CloseSession( ::hSession, ::hStatus )
   TF_DeleteSession( ::hSession, ::hStatus )
   TF_DeleteStatus( ::hStatus )
   TF_DeleteSessionOptions( ::hOptions )

   FreeLibrary( hDLL )

return nil

METHOD ImportGraph( cFileName ) CLASS TensorFlow

   local cGraph := MemoRead( cFileName )
   local hGraphDefOptions := TF_NewImportGraphDefOptions()
   
   TF_GraphImportGraphDef( ::hGraph, TF_NewBufferFromString( cGraph, Len( cGraph ) ), hGraphDefOptions, ::hStatus )
   
   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error importing a Graph file" )
   endif
   
   TF_DeleteImportGraphDefOptions( hGraphDefOptions )
   
return nil  

METHOD TensorNum( nValue ) CLASS TensorFlow

   local hTensor := TF_NewTensor( TF_INT32, 0, 0, @nValue, 4, 0, 0 )
   
return hTensor

METHOD TensorString( cString ) CLASS TensorFlow

   local hTensor := TF_AllocateTensor( TF_STRING, 0, 0, 8 + TF_StringEncodedSize( Len( cString ) ) )
   
   Memset( TF_TensorData( hTensor ), 0, 8 )
   
   TF_StringEncode( cString, Len( cString ), 8 + TF_TensorData( hTensor ), TF_StringEncodedSize( Len( cString ) ), ::hStatus )

   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error creating a Tensor string" )
   endif
   
return hTensor  

METHOD Variable( cVarName, nDataType ) CLASS TensorFlow

   local hOperationDescription := TF_NewOperation( ::hGraph, "Variable", cVarName )

   TF_SetAttrType( hOperationDescription, "dtype", nDataType )

return TF_FinishOperation( hOperationDescription, ::hStatus )

METHOD Constant( uValue, cName ) CLASS TensorFlow

   local hOperationDescription, hTensor
   
   do case
      case ValType( uValue ) == "C"
         hTensor = ::TensorString( uValue )
         
      case ValType( uValue ) == "N"
         hTensor = ::TensorNum( uValue )
   endcase

   hOperationDescription = TF_NewOperation( ::hGraph, "Const", cName )
   TF_SetAttrTensor( hOperationDescription, "value", hTensor, ::hStatus )
   TF_SetAttrType( hOperationDescription, "dtype", TF_TensorType( hTensor ) )

return TF_FinishOperation( hOperationDescription, ::hStatus )

METHOD Run( hOperation ) CLASS TensorFlow

   local hTensorOutput := 0

   TF_SessionRun( ::hSession, 0,;
                  0, 0, 0,;  // Inputs    
                  TF_Output( hOperation, 0 ), @hTensorOutput, 1,;  // Outputs
                  hOperation, 1,;  // Operations
                  0, ::hStatus )

   ::hTensorOutput = hTensorOutput

return nil

METHOD Output() CLASS TensorFlow

   local nType := TF_TensorType( ::hTensorOutput )
   local uValue
   
   do case
      case nType == TF_STRING
         uValue = TF_TensorString( TF_TensorData( ::hTensorOutput ) )
         
      case nType == TF_INT32  
         uValue = TF_TensorNum( TF_TensorData( ::hTensorOutput ) )
   endcase
   
return uValue

DLL FUNCTION TF_Version() AS LPSTR LIB hDLL

DLL FUNCTION TF_NewGraph() AS LONG LIB hDLL

DLL FUNCTION TF_NewSessionOptions() AS LONG LIB hDLL

DLL FUNCTION TF_NewStatus() AS LONG LIB hDLL

DLL FUNCTION TF_NewSession( hGraph AS LONG, hOptions AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_CloseSession( hSession AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteSession( hSession AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteStatus( hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteSessionOptions( hOptions AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_NewImportGraphDefOptions() AS LONG LIB hDLL

DLL FUNCTION TF_GraphImportGraphDef( hGraph AS LONG, hBuffer AS LONG, hGraphDefOptions AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_NewBufferFromString( cString AS LPSTR, nLegth AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_GetCode( hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_DeleteImportGraphDefOptions( hGraphDefOptions AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_NewTensor( nType AS LONG, pDims AS LONG, nDims AS LONG, @pData AS LONG, nLength AS LONG, pDeallocator AS LONG,;
                           pDeallocatorArgs AS LONG ) AS LONG LIB hDLL
                           
DLL FUNCTION TF_AllocateTensor( nType AS LONG, pDims AS LONG, nDims AS LONG, nLegth AS LONG ) AS LONG LIB hDLL
                           
DLL FUNCTION TF_StringEncodedSize( nLength AS LONG ) AS LONG LIB hDLL    

DLL FUNCTION TF_TensorData( hTensor AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_StringEncode( cString AS LPSTR, nLength AS LONG, pDest AS LONG, nDestLength AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_SessionRun( hSession AS LONG, hRunOptions AS LONG, hInputs AS LONG, @hInputValues AS LONG, nInputs AS LONG,;
                            hOutputs AS LONG, @hOutputValues AS LONG, nOutputs AS LONG, @hTargetOperations AS LONG, nTargets AS LONG,;
                            hRunMetadata AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_Message( hStatus AS LONG ) AS LPSTR LIB hDLL

DLL FUNCTION TF_NewOperation( hGraph AS LONG, cOperationType AS LPSTR, cOperationName AS LPSTR ) AS LONG LIB hDLL

DLL FUNCTION TF_SetAttrTensor( hOperationDescription AS LONG, cAttributeName AS LPSTR, hTensor AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_TensorType( hTensor AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_SetAttrType( hOperationDescription AS LONG, cAttributeName AS LPSTR, nDataType AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_FinishOperation( hOperationDescription AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

#pragma BEGINDUMP

#include <hbapi.h>

typedef struct TF_Output {
  void * oper;
  int index;
} TF_Output;

HB_FUNC( TF_OUTPUT )
{
   TF_Output * hOutput = ( TF_Output * ) hb_xgrab( sizeof( TF_Output ) );
   
   hOutput->oper = ( void * ) hb_parnll( 1 );
   hOutput->index = hb_parnl( 2 );
   
   hb_retnll( ( HB_LONGLONG ) hOutput );
}  

HB_FUNC( TF_TENSORSTRING )
{
   hb_retc( ( ( char * ) hb_parnll( 1 ) ) + 9 );
}  

HB_FUNC( TF_TENSORNUM )
{
   hb_retnl( hb_parnl( 1 ) );
}  

HB_FUNC( MEMSET )
{
   hb_retnll( ( HB_LONGLONG ) memset( ( void * ) hb_parnll( 1 ), hb_parnl( 2 ), hb_parnll( 3 ) ) );
}  

#pragma ENDDUMP
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Antonio Linares
Site Admin
 
Posts: 41289
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain

Re: TensorFlow DLL for Windows (64 bits)

Postby Antonio Linares » Wed Jun 07, 2017 3:43 pm

Testing a constant numeric value:

tf.prg
Code: Select all  Expand view
#include "FiveWin.ch"

#define TF_INT32   3
#define TF_STRING  7
#define TF_INT64   9

static hDLL

function Main()

   local oTF := TensorFlow():New()

   MsgInfo( oTF:Version() )

   oTF:Run( oTF:Constant( 5, "Five" ) )

   MsgInfo( oTF:Output() )

   oTF:End()

return nil

CLASS TensorFlow

   DATA hGraph
   DATA hOptions
   DATA hStatus
   DATA hSession
   DATA hTensorOutput

   METHOD New()
   
   METHOD Version() INLINE TF_Version()

   METHOD ImportGraph( cFileName )

   METHOD TensorNum( nValue )

   METHOD TensorString( cString )

   METHOD End()
   
   METHOD StatusCode() INLINE TF_GetCode( ::hStatus )

   METHOD Variable( cVarName, nDataType )

   METHOD Constant( uValue, cName )

   METHOD Run( hOperation )

   METHOD Output()

ENDCLASS

METHOD New() CLASS TensorFlow

   hDLL = LoadLibrary( "tensorflow.dll" )

   ::hGraph = TF_NewGraph()
   ::hOptions = TF_NewSessionOptions()
   ::hStatus = TF_NewStatus()
   ::hSession = TF_NewSession( ::hGraph, ::hOptions, ::hStatus )
     
return Self    

METHOD End() CLASS TensorFlow

   TF_CloseSession( ::hSession, ::hStatus )
   TF_DeleteSession( ::hSession, ::hStatus )
   TF_DeleteStatus( ::hStatus )
   TF_DeleteSessionOptions( ::hOptions )

   FreeLibrary( hDLL )

return nil

METHOD ImportGraph( cFileName ) CLASS TensorFlow

   local cGraph := MemoRead( cFileName )
   local hGraphDefOptions := TF_NewImportGraphDefOptions()
   
   TF_GraphImportGraphDef( ::hGraph, TF_NewBufferFromString( cGraph, Len( cGraph ) ), hGraphDefOptions, ::hStatus )
   
   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error importing a Graph file" )
   endif
   
   TF_DeleteImportGraphDefOptions( hGraphDefOptions )
   
return nil  

METHOD TensorNum( nValue ) CLASS TensorFlow

   local hTensor := TF_AllocateTensor( TF_INT64, 0, 0, 8 )
   
   Memset( TF_TensorData( hTensor ), 0, 8 )
   // Memset( TF_TensorData( hTensor ), nValue, 1 )
   Memcpy( TF_TensorData( hTensor ), L2Bin( nValue ), Len( L2Bin( nValue ) ) )
   
return hTensor

METHOD TensorString( cString ) CLASS TensorFlow

   local hTensor := TF_AllocateTensor( TF_STRING, 0, 0, 8 + TF_StringEncodedSize( Len( cString ) ) )
   
   Memset( TF_TensorData( hTensor ), 0, 8 )
   
   TF_StringEncode( cString, Len( cString ), 8 + TF_TensorData( hTensor ), TF_StringEncodedSize( Len( cString ) ), ::hStatus )

   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error creating a Tensor string" )
   endif
   
return hTensor  

METHOD Variable( cVarName, nDataType ) CLASS TensorFlow

   local hOperationDescription := TF_NewOperation( ::hGraph, "Variable", cVarName )

   TF_SetAttrType( hOperationDescription, "dtype", nDataType )

return TF_FinishOperation( hOperationDescription, ::hStatus )

METHOD Constant( uValue, cName ) CLASS TensorFlow

   local hOperationDescription, hTensor
   
   do case
      case ValType( uValue ) == "C"
         hTensor = ::TensorString( uValue )
         
      case ValType( uValue ) == "N"
         hTensor = ::TensorNum( uValue )
   endcase

   hOperationDescription = TF_NewOperation( ::hGraph, "Const", cName )
   TF_SetAttrTensor( hOperationDescription, "value", hTensor, ::hStatus )
   TF_SetAttrType( hOperationDescription, "dtype", TF_TensorType( hTensor ) )

return TF_FinishOperation( hOperationDescription, ::hStatus )

METHOD Run( hOperation ) CLASS TensorFlow

   local hTensorOutput := 0

   TF_SessionRun( ::hSession, 0,;
                  0, 0, 0,;  // Inputs    
                  TF_Output( hOperation, 0 ), @hTensorOutput, 1,;  // Outputs
                  hOperation, 1,;  // Operations
                  0, ::hStatus )

   ::hTensorOutput = hTensorOutput

return nil

METHOD Output() CLASS TensorFlow

   local nType := TF_TensorType( ::hTensorOutput )
   local uValue
   
   do case
      case nType == TF_STRING
         uValue = TF_TensorString( TF_TensorData( ::hTensorOutput ) )
         
      case nType == TF_INT64  
         uValue = TF_TensorNum( TF_TensorData( ::hTensorOutput ) )
         
      otherwise
         MsgAlert( "type not supported in Method Output yet", nType )
   endcase
   
return uValue

DLL FUNCTION TF_Version() AS LPSTR LIB hDLL

DLL FUNCTION TF_NewGraph() AS LONG LIB hDLL

DLL FUNCTION TF_NewSessionOptions() AS LONG LIB hDLL

DLL FUNCTION TF_NewStatus() AS LONG LIB hDLL

DLL FUNCTION TF_NewSession( hGraph AS LONG, hOptions AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_CloseSession( hSession AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteSession( hSession AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteStatus( hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteSessionOptions( hOptions AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_NewImportGraphDefOptions() AS LONG LIB hDLL

DLL FUNCTION TF_GraphImportGraphDef( hGraph AS LONG, hBuffer AS LONG, hGraphDefOptions AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_NewBufferFromString( cString AS LPSTR, nLegth AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_GetCode( hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_DeleteImportGraphDefOptions( hGraphDefOptions AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_NewTensor( nType AS LONG, @pDims AS LONG, nDims AS LONG, @pData AS LONG, nLength AS LONG, pDeallocator AS LONG,;
                           pDeallocatorArgs AS LONG ) AS LONG LIB hDLL
                           
DLL FUNCTION TF_AllocateTensor( nType AS LONG, pDims AS LONG, nDims AS LONG, nLegth AS LONG ) AS LONG LIB hDLL
                           
DLL FUNCTION TF_StringEncodedSize( nLength AS LONG ) AS LONG LIB hDLL    

DLL FUNCTION TF_TensorData( hTensor AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_StringEncode( cString AS LPSTR, nLength AS LONG, pDest AS LONG, nDestLength AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_SessionRun( hSession AS LONG, hRunOptions AS LONG, hInputs AS LONG, @hInputValues AS LONG, nInputs AS LONG,;
                            hOutputs AS LONG, @hOutputValues AS LONG, nOutputs AS LONG, @hTargetOperations AS LONG, nTargets AS LONG,;
                            hRunMetadata AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_Message( hStatus AS LONG ) AS LPSTR LIB hDLL

DLL FUNCTION TF_NewOperation( hGraph AS LONG, cOperationType AS LPSTR, cOperationName AS LPSTR ) AS LONG LIB hDLL

DLL FUNCTION TF_SetAttrTensor( hOperationDescription AS LONG, cAttributeName AS LPSTR, hTensor AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_TensorType( hTensor AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_SetAttrType( hOperationDescription AS LONG, cAttributeName AS LPSTR, nDataType AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_FinishOperation( hOperationDescription AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

#pragma BEGINDUMP

#include <hbapi.h>

typedef struct TF_Output {
  void * oper;
  int index;
} TF_Output;

HB_FUNC( TF_OUTPUT )
{
   TF_Output * hOutput = ( TF_Output * ) hb_xgrab( sizeof( TF_Output ) );
   
   hOutput->oper = ( void * ) hb_parnll( 1 );
   hOutput->index = hb_parnl( 2 );
   
   hb_retnll( ( HB_LONGLONG ) hOutput );
}  

HB_FUNC( TF_TENSORSTRING )
{
   hb_retc( ( ( char * ) hb_parnll( 1 ) ) + 9 );
}  

HB_FUNC( TF_TENSORNUM )
{
   hb_retnl( * ( int * ) hb_parnll( 1 ) );
}  

HB_FUNC( MEMSET )
{
   hb_retnll( ( HB_LONGLONG ) memset( ( void * ) hb_parnll( 1 ), hb_parnl( 2 ), hb_parnll( 3 ) ) );
}  

HB_FUNC( MEMCPY )
{
   hb_retnll( ( HB_LONGLONG ) memcpy( ( void * ) hb_parnll( 1 ), ( void * ) hb_parc( 2 ), hb_parnll( 3 ) ) );
}  

#pragma ENDDUMP
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Antonio Linares
Site Admin
 
Posts: 41289
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain

Re: TensorFlow DLL for Windows (64 bits)

Postby karinha » Thu Jun 08, 2017 2:54 pm

Maestro, desculpe mi ignorancia, pero para qué sirve TensorFlow() ?

Regards, saludos.
João Santos - São Paulo - Brasil - Phone: +55(11)95150-7341
User avatar
karinha
 
Posts: 7190
Joined: Tue Dec 20, 2005 7:36 pm
Location: São Paulo - Brasil

Re: TensorFlow DLL for Windows (64 bits)

Postby Antonio Linares » Thu Jun 08, 2017 6:49 pm

Joao,

TensorFlow is a Machine Learning (AI) software developed by Google which is becoming very popular

An open-source software library for Machine Intelligence


https://www.tensorflow.org/

Examples of use:
https://cloud.google.com/blog/big-data/2016/08/how-a-japanese-cucumber-farmer-is-using-deep-learning-and-tensorflow

https://www.theverge.com/2016/1/21/10805398/friends-neural-network-scripts

Possibilities are endless :-)
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Antonio Linares
Site Admin
 
Posts: 41289
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain

Re: TensorFlow DLL for Windows (64 bits)

Postby Antonio Linares » Fri Jun 09, 2017 6:09 am

Adding two constant numbers:

tf.prg
Code: Select all  Expand view
#include "FiveWin.ch"

#define TF_STRING  7
#define TF_INT64   9

static hDLL

function Main()

   local oTF := TensorFlow():New()

   MsgInfo( oTF:Version() )

   oTF:Run( oTF:Add( oTF:Constant( 5, "Five" ), oTF:Constant( 3, "three" ) ) )

   MsgInfo( oTF:Output() )

   oTF:End()

return nil

CLASS TensorFlow

   DATA hGraph
   DATA hOptions
   DATA hStatus
   DATA hSession
   DATA hTensorOutput

   METHOD New()
   
   METHOD Add( hOperation1, hOperation1, cName )
   
   METHOD Version() INLINE TF_Version()

   METHOD ImportGraph( cFileName )

   METHOD TensorNum( nValue )

   METHOD TensorString( cString )

   METHOD End()
   
   METHOD StatusCode() INLINE TF_GetCode( ::hStatus )

   METHOD Variable( cVarName, nDataType )

   METHOD Constant( uValue, cName )

   METHOD Run( hOperation )

   METHOD Output()

ENDCLASS

METHOD New() CLASS TensorFlow

   hDLL = LoadLibrary( "tensorflow.dll" )

   ::hGraph = TF_NewGraph()
   ::hOptions = TF_NewSessionOptions()
   ::hStatus = TF_NewStatus()
   ::hSession = TF_NewSession( ::hGraph, ::hOptions, ::hStatus )
     
return Self    

METHOD End() CLASS TensorFlow

   TF_CloseSession( ::hSession, ::hStatus )
   TF_DeleteSession( ::hSession, ::hStatus )
   TF_DeleteStatus( ::hStatus )
   TF_DeleteSessionOptions( ::hOptions )

   FreeLibrary( hDLL )

return nil

METHOD Add( hOperation1, hOperation2, cName ) CLASS TensorFlow

   local hOperationDescription := TF_NewOperation( ::hGraph, "AddN", If( cName == nil, "AddN", cName ) )
   local hOperation, hOutput
   
   TF_AddInputList( hOperationDescription, hOutput := TF_Output2( hOperation1, hOperation2 ), 2 )

   hOperation = TF_FinishOperation( hOperationDescription, ::hStatus )
   
   hb_xfree( hOutput )
   
   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error creating AddN operator: " + Str( TF_GetCode( ::hStatus ) ))
   endif
   
return hOperation

METHOD ImportGraph( cFileName ) CLASS TensorFlow

   local cGraph := MemoRead( cFileName )
   local hGraphDefOptions := TF_NewImportGraphDefOptions()
   
   TF_GraphImportGraphDef( ::hGraph, TF_NewBufferFromString( cGraph, Len( cGraph ) ), hGraphDefOptions, ::hStatus )
   
   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error importing a Graph file" )
   endif
   
   TF_DeleteImportGraphDefOptions( hGraphDefOptions )
   
return nil  

METHOD TensorNum( nValue ) CLASS TensorFlow

   local hTensor := TF_AllocateTensor( TF_INT64, 0, 0, 8 )
   
   Memset( TF_TensorData( hTensor ), 0, 8 )
   Memcpy( TF_TensorData( hTensor ), L2Bin( nValue ), Len( L2Bin( nValue ) ) )
   
return hTensor

METHOD TensorString( cString ) CLASS TensorFlow

   local hTensor := TF_AllocateTensor( TF_STRING, 0, 0, 8 + TF_StringEncodedSize( Len( cString ) ) )
   
   Memset( TF_TensorData( hTensor ), 0, 8 )
   
   TF_StringEncode( cString, Len( cString ), 8 + TF_TensorData( hTensor ), TF_StringEncodedSize( Len( cString ) ), ::hStatus )

   if TF_GetCode( ::hStatus ) != 0
      MsgAlert( TF_Message( ::hStatus ), "Error creating a Tensor string" )
   endif
   
return hTensor  

METHOD Variable( cVarName, nDataType ) CLASS TensorFlow

   local hOperationDescription := TF_NewOperation( ::hGraph, "Variable", cVarName )

   TF_SetAttrType( hOperationDescription, "dtype", nDataType )

return TF_FinishOperation( hOperationDescription, ::hStatus )

METHOD Constant( uValue, cName ) CLASS TensorFlow

   local hOperationDescription, hTensor
   
   do case
      case ValType( uValue ) == "C"
         hTensor = ::TensorString( uValue )
         
      case ValType( uValue ) == "N"
         hTensor = ::TensorNum( uValue )
   endcase

   hOperationDescription = TF_NewOperation( ::hGraph, "Const", cName )
   TF_SetAttrTensor( hOperationDescription, "value", hTensor, ::hStatus )
   TF_SetAttrType( hOperationDescription, "dtype", TF_TensorType( hTensor ) )

return TF_FinishOperation( hOperationDescription, ::hStatus )

METHOD Run( hOperation ) CLASS TensorFlow

   local hTensorOutput := 0, hOutput

   TF_SessionRun( ::hSession, 0,;
                  0, 0, 0,;  // Inputs    
                  hOutput := TF_Output( hOperation, 0 ), @hTensorOutput, 1,;  // Outputs
                  hOperation, 1,;  // Operations
                  0, ::hStatus )

   hb_xfree( hOutput )
   
   ::hTensorOutput = hTensorOutput

return nil

METHOD Output() CLASS TensorFlow

   local nType := TF_TensorType( ::hTensorOutput )
   local uValue
   
   do case
      case nType == TF_STRING
         uValue = TF_TensorString( TF_TensorData( ::hTensorOutput ) )
         
      case nType == TF_INT64  
         uValue = TF_TensorNum( TF_TensorData( ::hTensorOutput ) )
         
      otherwise
         MsgAlert( "type not supported in Method Output yet", nType )
   endcase
   
return uValue

DLL FUNCTION TF_Version() AS LPSTR LIB hDLL

DLL FUNCTION TF_NewGraph() AS LONG LIB hDLL

DLL FUNCTION TF_NewSessionOptions() AS LONG LIB hDLL

DLL FUNCTION TF_NewStatus() AS LONG LIB hDLL

DLL FUNCTION TF_NewSession( hGraph AS LONG, hOptions AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_CloseSession( hSession AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteSession( hSession AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteStatus( hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_DeleteSessionOptions( hOptions AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_NewImportGraphDefOptions() AS LONG LIB hDLL

DLL FUNCTION TF_GraphImportGraphDef( hGraph AS LONG, hBuffer AS LONG, hGraphDefOptions AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_NewBufferFromString( cString AS LPSTR, nLegth AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_GetCode( hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_DeleteImportGraphDefOptions( hGraphDefOptions AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_NewTensor( nType AS LONG, @pDims AS LONG, nDims AS LONG, @pData AS LONG, nLength AS LONG, pDeallocator AS LONG,;
                           pDeallocatorArgs AS LONG ) AS LONG LIB hDLL
                           
DLL FUNCTION TF_AllocateTensor( nType AS LONG, pDims AS LONG, nDims AS LONG, nLegth AS LONG ) AS LONG LIB hDLL
                           
DLL FUNCTION TF_StringEncodedSize( nLength AS LONG ) AS LONG LIB hDLL    

DLL FUNCTION TF_TensorData( hTensor AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_StringEncode( cString AS LPSTR, nLength AS LONG, pDest AS LONG, nDestLength AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_SessionRun( hSession AS LONG, hRunOptions AS LONG, hInputs AS LONG, @hInputValues AS LONG, nInputs AS LONG,;
                            hOutputs AS LONG, @hOutputValues AS LONG, nOutputs AS LONG, @hTargetOperations AS LONG, nTargets AS LONG,;
                            hRunMetadata AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_Message( hStatus AS LONG ) AS LPSTR LIB hDLL

DLL FUNCTION TF_NewOperation( hGraph AS LONG, cOperationType AS LPSTR, cOperationName AS LPSTR ) AS LONG LIB hDLL

DLL FUNCTION TF_SetAttrTensor( hOperationDescription AS LONG, cAttributeName AS LPSTR, hTensor AS LONG, hStatus AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_TensorType( hTensor AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_SetAttrType( hOperationDescription AS LONG, cAttributeName AS LPSTR, nDataType AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_FinishOperation( hOperationDescription AS LONG, hStatus AS LONG ) AS LONG LIB hDLL

DLL FUNCTION TF_AddInput( hOperationDescription AS LONG, nInput AS LONG ) AS VOID LIB hDLL

DLL FUNCTION TF_AddInputList( hOperationDescription AS LONG, hInputs AS LONG, nInputs AS LONG ) AS VOID LIB hDLL

#pragma BEGINDUMP

#include <hbapi.h>

typedef struct TF_Output {
  void * oper;
  int index;
} TF_Output;

HB_FUNC( TF_OUTPUT )
{
   TF_Output * hOutput = ( TF_Output * ) hb_xgrab( sizeof( TF_Output ) );
   
   hOutput->oper = ( void * ) hb_parnll( 1 );
   hOutput->index = hb_parnl( 2 );
   
   hb_retnll( ( HB_LONGLONG ) hOutput );
}  

HB_FUNC( TF_OUTPUT2 )
{
   TF_Output * hOutput = ( TF_Output * ) hb_xgrab( sizeof( TF_Output ) * 2 );
   
   hOutput[ 0 ].oper = ( void * ) hb_parnll( 1 );
   hOutput[ 0 ].index = 0;
   hOutput[ 1 ].oper = ( void * ) hb_parnll( 2 );
   hOutput[ 1 ].index = 0;
   
   hb_retnll( ( HB_LONGLONG ) hOutput );
}  

HB_FUNC( TF_TENSORSTRING )
{
   hb_retc( ( ( char * ) hb_parnll( 1 ) ) + 9 );
}  

HB_FUNC( TF_TENSORNUM )
{
   hb_retnl( * ( int * ) hb_parnll( 1 ) );
}  

HB_FUNC( MEMSET )
{
   hb_retnll( ( HB_LONGLONG ) memset( ( void * ) hb_parnll( 1 ), hb_parnl( 2 ), hb_parnll( 3 ) ) );
}  

HB_FUNC( MEMCPY )
{
   hb_retnll( ( HB_LONGLONG ) memcpy( ( void * ) hb_parnll( 1 ), ( void * ) hb_parc( 2 ), hb_parnll( 3 ) ) );
}  

HB_FUNC( HB_XFREE )
{
   hb_xfree( ( void * ) hb_parnll( 1 ) );
}  

#pragma ENDDUMP


Image
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Antonio Linares
Site Admin
 
Posts: 41289
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain

Re: TensorFlow DLL for Windows (64 bits)

Postby cnavarro » Fri Jun 09, 2017 6:57 pm

Great Antonio, very good
Cristobal Navarro
Hay dos tipos de personas: las que te hacen perder el tiempo y las que te hacen perder la noción del tiempo
El secreto de la felicidad no está en hacer lo que te gusta, sino en que te guste lo que haces
User avatar
cnavarro
 
Posts: 6500
Joined: Wed Feb 15, 2012 8:25 pm
Location: España

Re: TensorFlow DLL for Windows (64 bits)

Postby Antonio Linares » Mon Jun 12, 2017 12:47 pm

regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Antonio Linares
Site Admin
 
Posts: 41289
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain

Re: TensorFlow DLL for Windows (64 bits)

Postby Antonio Linares » Tue Jun 20, 2017 10:11 pm

Accelerating Deep Learning Research with the Tensor2Tensor Library

https://research.googleblog.com/2017/06/accelerating-deep-learning-research.html?m=1
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Antonio Linares
Site Admin
 
Posts: 41289
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain

Re: TensorFlow DLL for Windows (64 bits)

Postby Antonio Linares » Mon Jul 31, 2017 3:46 pm

regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Antonio Linares
Site Admin
 
Posts: 41289
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain

Re: TensorFlow DLL for Windows (64 bits)

Postby jnavas » Sun Nov 11, 2018 2:11 am

Antonio
saludos, excelente trabajo.
En este video, explican su aplicación, me interesa aplicarlo en las tendencias de ventas.
https://youtu.be/E7iBIzEhKnQ
User avatar
jnavas
 
Posts: 472
Joined: Wed Nov 16, 2005 12:03 pm
Location: Caracas - Venezuela

Previous

Return to TensorFlow.dll for Harbour and FWH

Who is online

Users browsing this forum: No registered users and 2 guests