@@ -445,7 +445,63 @@ make_row(ErlNifEnv* env, sqlite3_stmt* statement)
445445
446446 enif_free (columns );
447447
448- return enif_make_tuple2 (env , make_atom (env , "row" ), row );
448+ return row ;
449+ }
450+
451+ static ERL_NIF_TERM
452+ exqlite_multi_step (ErlNifEnv * env , int argc , const ERL_NIF_TERM argv [])
453+ {
454+ assert (env );
455+
456+ statement_t * statement = NULL ;
457+ connection_t * conn = NULL ;
458+ int chunk_size ;
459+
460+ if (argc != 3 ) {
461+ return enif_make_badarg (env );
462+ }
463+
464+ if (!enif_get_resource (env , argv [0 ], connection_type , (void * * )& conn )) {
465+ return make_error_tuple (env , "invalid_connection" );
466+ }
467+
468+ if (!enif_get_resource (env , argv [1 ], statement_type , (void * * )& statement )) {
469+ return make_error_tuple (env , "invalid_statement" );
470+ }
471+
472+ if (!enif_get_int (env , argv [2 ], & chunk_size )) {
473+ return make_error_tuple (env , "invalid_chunk_size" );
474+ }
475+
476+ if (chunk_size < 1 ) {
477+ return make_error_tuple (env , "invalid_chunk_size" );
478+ }
479+
480+ ERL_NIF_TERM rows = enif_make_list_from_array (env , NULL , 0 );
481+ for (int i = 0 ; i < chunk_size ; i ++ ) {
482+ ERL_NIF_TERM row ;
483+
484+ int rc = sqlite3_step (statement -> statement );
485+ switch (rc ) {
486+ case SQLITE_BUSY :
487+ sqlite3_reset (statement -> statement );
488+ return make_atom (env , "busy" );
489+
490+ case SQLITE_DONE :
491+ return enif_make_tuple2 (env , make_atom (env , "done" ), rows );
492+
493+ case SQLITE_ROW :
494+ row = make_row (env , statement -> statement );
495+ rows = enif_make_list_cell (env , row , rows );
496+ break ;
497+
498+ default :
499+ sqlite3_reset (statement -> statement );
500+ return make_sqlite3_error_tuple (env , rc , conn -> db );
501+ }
502+ }
503+
504+ return enif_make_tuple2 (env , make_atom (env , "rows" ), rows );
449505}
450506
451507static ERL_NIF_TERM
@@ -471,7 +527,11 @@ exqlite_step(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[])
471527 int rc = sqlite3_step (statement -> statement );
472528 switch (rc ) {
473529 case SQLITE_ROW :
474- return make_row (env , statement -> statement );
530+ return enif_make_tuple2 (
531+ env ,
532+ make_atom (env , "row" ),
533+ make_row (env , statement -> statement )
534+ );
475535 case SQLITE_BUSY :
476536 return make_atom (env , "busy" );
477537 case SQLITE_DONE :
@@ -642,6 +702,7 @@ static ErlNifFunc nif_funcs[] = {
642702 {"prepare" , 2 , exqlite_prepare , ERL_NIF_DIRTY_JOB_IO_BOUND },
643703 {"bind" , 3 , exqlite_bind , ERL_NIF_DIRTY_JOB_IO_BOUND },
644704 {"step" , 2 , exqlite_step , ERL_NIF_DIRTY_JOB_IO_BOUND },
705+ {"multi_step" , 3 , exqlite_multi_step , ERL_NIF_DIRTY_JOB_IO_BOUND },
645706 {"columns" , 2 , exqlite_columns , ERL_NIF_DIRTY_JOB_IO_BOUND },
646707 {"last_insert_rowid" , 1 , exqlite_last_insert_rowid , ERL_NIF_DIRTY_JOB_IO_BOUND },
647708 {"transaction_status" , 1 , exqlite_transaction_status , ERL_NIF_DIRTY_JOB_IO_BOUND },
0 commit comments