diff --git a/lib/Huawei/Hilink.pm b/lib/Huawei/Hilink.pm
index 7a83ae3e7d1c08fa3e5a56971101948e8a49ede0..239e83118f252bd8a6c89fd2e807cead40b9ae10 100755
--- a/lib/Huawei/Hilink.pm
+++ b/lib/Huawei/Hilink.pm
@@ -10,6 +10,7 @@ $Data::Dumper::Indent= 1;
 use HTTP::Request;
 use LWP::UserAgent;
 use XML::Simple;
+use Encode;
 
 my $verbose= 0;
 my $debug= 0;
@@ -17,7 +18,7 @@ my $standalone= 0;
 
 my %queries=
 (
-  'information'        => { api => '/api/device/information',   auth => 'none' },
+  'information'        => { api => '/api/device/information',   auth => 'none' }, # returns DeviceName, Msisdn (aka. telnr.), imei, imsi, ..., WanIPAddress, WanIPv6Address, etc.
   'signal'             => { api => '/api/device/signal',        auth => 'none' },
   'module-switch'      => { api => '/api/global/module-switch', auth => 'none' },
   'current-plmn'       => { api => '/api/net/current-plmn',     auth => 'none' },
@@ -26,7 +27,7 @@ my %queries=
   'converged-status'   => { api => '/api/monitoring/converged-status',   auth => 'none' },
 
   'traffic-statistics' => { api => '/api/monitoring/traffic-statistics', auth => 'token' },
-  'status'             => { api => '/api/monitoring/status',             auth => 'token' },
+  'status'             => { api => '/api/monitoring/status',             auth => 'token' }, # returns PrimaryDns, SecondaryDns, etc.
 
   # does not work
 # 'sms-list'           => { api => '/api/sms/sms-list',             auth => 'token' },
@@ -61,7 +62,7 @@ sub get_session
 {
   my $self= shift;
 
-  return ($self->{_session_id}, $self->{_token}) if (exists($self->{_session_id}) && exists ($self->{_token}));
+  # return ($self->{_session_id}, $self->{_token}) if (exists($self->{_session_id}) && exists ($self->{_token}));
  
   my $url= 'http://' . $self->{gwip} . '/api/webserver/SesTokInfo';
   my $ua= $self->{_ua} || ($self->{_ua}= new LWP::UserAgent());
@@ -76,7 +77,7 @@ sub get_session
 
   # print __LINE__, " sess=[$sess]\n" if ($debug);
   my $ref= XMLin($sess);
-  # print __LINE__, " ref: ", Dumper($ref);
+  # print __LINE__, " ref: ", Dumper($ref) if ($debug);
   return ($self->{_session_id}= $ref->{SesInfo}, $self->{_token}= $ref->{TokInfo}) if (defined ($ref));
 
   (undef, undef);
@@ -94,31 +95,61 @@ sub send_sms
     print __LINE__, " no session_id obtained\n" if ($debug);
     return undef;
   }
+  # print __LINE__, " session_id=[$session_id]\n";
 
   print __LINE__, " send-sms phone=[$phone] message=[$message]\n" if ($debug);
 
   my $url= 'http://'. $self->{gwip}. '/api/sms/send-sms';
-
+  
+  # my $message_iso8859= Encode::encode("ISO-8859-1", $message);
   my $submit_data= "<?xml version='1.0' encoding='UTF-8'?><request><Index>-1</Index><Phones><Phone>$phone</Phone></Phones><Sca></Sca><Content>$message</Content><Length>-1</Length><Reserved>1</Reserved><Date>-1</Date></request>";
 
   my $ua= $self->{_ua} || ($self->{_ua}= new LWP::UserAgent());
   $ua->default_header('Cookie', $session_id);
   $ua->default_header(':__RequestVerificationToken', $token); # prevent header name canonication, see perldoc HTTP::Headers under NON-CANONICALIZED FIELD NAMES
 
-  my $resp= $ua->post($url, 'Content-Type' => 'text/html', 'Content' => $submit_data);
+  my $resp= $ua->post($url, 'Content-Type' => 'text/html; charset=UTF-8', 'Content' => $submit_data);
   unless ($resp->is_success)
   {
     print __LINE__, " ua failed: ", $resp->status_line, "\n";
     return (undef, undef);
   }
   my $result_data= $resp->decoded_content;
-  print __LINE__, " result_data=[$result_data]\n";
+  print __LINE__, " result_data=[$result_data]\n" if ($debug);
   my $ref= XMLin($result_data);
-  print __LINE__, " ref: ", Dumper($ref) if ($debug || $standalone);
+  print __LINE__, " ref=[$ref]: ", Dumper($ref) if ($debug);
+
+  if ($ref eq 'OK') { $ref= { status => 'OK' }; }
+  else { $ref->{status}= 'ERROR'; }
+  print __LINE__, " ref=[$ref]: ", Dumper($ref) if ($debug);
 
   $ref;
 }
 
+sub send_sms_with_retries
+{
+  my $obj= shift;
+  my $nr= shift;
+  my $msg= shift;
+  my $max_retries= shift || 5;
+  my $sleep= shift || 1; # sleep at least one second between retries
+
+  my $res;
+  for (my $retries= 1; $retries <= $max_retries; $retries++)
+  {
+    $res= $obj->send_sms($nr, $msg);
+    last if ($res->{status} eq 'OK' || $res->{code} ne '113004'); # 113004
+    print __LINE__, " sleeping $sleep seconds for retry nr. $retries\n";
+    sleep($sleep);
+  }
+
+      # $obj->list_sms(1); works
+      # $obj->query('status');
+      # sleep(5);
+
+  $res;
+}
+
 sub list_sms
 {
   my $self= shift;
@@ -226,7 +257,17 @@ sub main
 
   my $op_code= shift (@PARS);
   print __LINE__, " op_code=[$op_code]\n" if ($debug);
-     if ($op_code eq 'send-sms') { $obj->send_sms(@PARS); } 
+
+  if ($op_code eq 'send-sms')
+  {
+    my $nr= shift (@PARS);
+    while (defined (my $msg= shift (@PARS)))
+    {
+      my $res= $obj->send_sms_with_retries($nr, $msg);
+      print __LINE__, " res: ", Dumper($res);
+      sleep(1) if (@PARS);
+    }
+  } 
   elsif ($op_code eq 'list-sms') { $obj->list_sms(@PARS); } 
   elsif (exists($queries{$op_code})) { $obj->query($op_code); } 
 
@@ -241,4 +282,9 @@ __END__
 
 =head1 AUTHOR
 
+=head1 ERROR CODES
+
+ 100005 .. HTML encoding error?
+ 113004 .. returned when sms sent too quickly after the first one.
+ 125003 .. returned when get_session was not called before