stringio 3.0.2 → 3.0.3

Sign up to get free protection for your applications and to get access to all the features.
Files changed (3) hide show
  1. checksums.yaml +4 -4
  2. data/ext/stringio/stringio.c +241 -132
  3. metadata +3 -3
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 36d42b708a5834d7fb5b4fc7080f995fa620aa8a579515a3be446e952bb795db
4
- data.tar.gz: d41342f6f4f5ea0046f21bb1274f856e38f01420de77176518cf3cc135208337
3
+ metadata.gz: a315b6faaaa7115f4216b4faeecf4297bc7c649518496fc26513b614acd2a777
4
+ data.tar.gz: fc0c0a7d6ac4f813a05384450aa391ce875216050814e13c835a0a2d3a02dd03
5
5
  SHA512:
6
- metadata.gz: a8a9f45ac75b1baa8bb8c0e91bc45eb556329a40e5211ecf3525bd3fb089fc9e39a19e1f1671e0f7c8e79a8b24e27464a6e307e74c6a69d9fd32ccf849ced938
7
- data.tar.gz: eb2c1d93bc7a91ee5bff2aeaeb64f1e2d5817358447fd26fe65bfc4a48ef3745087fa169289139b3b7e408baca4dd66517a86764bcbd3a67a4b0f2e0d600f863
6
+ metadata.gz: 19a578a1a114c4bf560c395cc849cbf901fc16a1dbda24016c70364c65c5f9d92aa73f42fe8e606d562073d5af0cabaf9f5a707aa8c9bce288b6d2b3b0c99f3e
7
+ data.tar.gz: a09d036c619b8fea588276aa22ba31253ed325d310ff896d5c8577b3c80aa1f9fb2d686a25955a2638826c94a23cfe1902f530a9d7bef8f07518c95269864906
@@ -12,7 +12,7 @@
12
12
 
13
13
  **********************************************************************/
14
14
 
15
- #define STRINGIO_VERSION "3.0.2"
15
+ #define STRINGIO_VERSION "3.0.3"
16
16
 
17
17
  #include "ruby.h"
18
18
  #include "ruby/io.h"
@@ -67,15 +67,20 @@ strio_extract_modeenc(VALUE *vmode_p, VALUE *vperm_p, VALUE opthash,
67
67
  e = strchr(++n, ':');
68
68
  len = e ? e - n : (long)strlen(n);
69
69
  if (len > 0 && len <= ENCODING_MAXNAMELEN) {
70
+ rb_encoding *enc;
70
71
  if (e) {
71
72
  memcpy(encname, n, len);
72
73
  encname[len] = '\0';
73
74
  n = encname;
74
75
  }
75
- convconfig_p->enc = rb_enc_find(n);
76
+ enc = rb_enc_find(n);
77
+ if (e)
78
+ convconfig_p->enc2 = enc;
79
+ else
80
+ convconfig_p->enc = enc;
76
81
  }
77
82
  if (e && (len = strlen(++e)) > 0 && len <= ENCODING_MAXNAMELEN) {
78
- convconfig_p->enc2 = rb_enc_find(e);
83
+ convconfig_p->enc = rb_enc_find(e);
79
84
  }
80
85
  }
81
86
  }
@@ -252,9 +257,20 @@ strio_s_allocate(VALUE klass)
252
257
  }
253
258
 
254
259
  /*
255
- * call-seq: StringIO.new(string=""[, mode])
260
+ * call-seq:
261
+ * StringIO.new(string = '', mode = 'r+') -> new_stringio
262
+ *
263
+ * Note that +mode+ defaults to <tt>'r'</tt> if +string+ is frozen.
264
+ *
265
+ * Returns a new \StringIO instance formed from +string+ and +mode+;
266
+ * see {Access Modes}[https://docs.ruby-lang.org/en/master/File.html#class-File-label-Access+Modes]:
256
267
  *
257
- * Creates new StringIO instance from with _string_ and _mode_.
268
+ * strio = StringIO.new # => #<StringIO>
269
+ * strio.close
270
+ *
271
+ * The instance should be closed when no longer needed.
272
+ *
273
+ * Related: StringIO.open (accepts block; closes automatically).
258
274
  */
259
275
  static VALUE
260
276
  strio_initialize(int argc, VALUE *argv, VALUE self)
@@ -387,11 +403,26 @@ strio_finalize(VALUE self)
387
403
  }
388
404
 
389
405
  /*
390
- * call-seq: StringIO.open(string=""[, mode]) {|strio| ...}
406
+ * call-seq:
407
+ * StringIO.open(string = '', mode = 'r+') {|strio| ... }
408
+ *
409
+ * Note that +mode+ defaults to <tt>'r'</tt> if +string+ is frozen.
410
+ *
411
+ * Creates a new \StringIO instance formed from +string+ and +mode+;
412
+ * see {Access Modes}[https://docs.ruby-lang.org/en/master/File.html#class-File-label-Access+Modes].
413
+ *
414
+ * With no block, returns the new instance:
415
+ *
416
+ * strio = StringIO.open # => #<StringIO>
417
+ *
418
+ * With a block, calls the block with the new instance
419
+ * and returns the block's value;
420
+ * closes the instance on block exit.
391
421
  *
392
- * Equivalent to StringIO.new except that when it is called with a block, it
393
- * yields with the new instance and closes it, and returns the result which
394
- * returned from the block.
422
+ * StringIO.open {|strio| p strio }
423
+ * # => #<StringIO>
424
+ *
425
+ * Related: StringIO.new.
395
426
  */
396
427
  static VALUE
397
428
  strio_s_open(int argc, VALUE *argv, VALUE klass)
@@ -477,9 +508,23 @@ strio_unimpl(int argc, VALUE *argv, VALUE self)
477
508
  }
478
509
 
479
510
  /*
480
- * call-seq: strio.string -> string
511
+ * call-seq:
512
+ * string -> string
513
+ *
514
+ * Returns underlying string:
515
+ *
516
+ * StringIO.open('foo') do |strio|
517
+ * p strio.string
518
+ * strio.string = 'bar'
519
+ * p strio.string
520
+ * end
521
+ *
522
+ * Output:
523
+ *
524
+ * "foo"
525
+ * "bar"
481
526
  *
482
- * Returns underlying String object, the subject of IO.
527
+ * Related: StringIO#string= (assigns the underlying string).
483
528
  */
484
529
  static VALUE
485
530
  strio_get_string(VALUE self)
@@ -489,9 +534,23 @@ strio_get_string(VALUE self)
489
534
 
490
535
  /*
491
536
  * call-seq:
492
- * strio.string = string -> string
537
+ * string = other_string -> other_string
493
538
  *
494
- * Changes underlying String object, the subject of IO.
539
+ * Assigns the underlying string as +other_string+, and sets position to zero;
540
+ * returns +other_string+:
541
+ *
542
+ * StringIO.open('foo') do |strio|
543
+ * p strio.string
544
+ * strio.string = 'bar'
545
+ * p strio.string
546
+ * end
547
+ *
548
+ * Output:
549
+ *
550
+ * "foo"
551
+ * "bar"
552
+ *
553
+ * Related: StringIO#string (returns the underlying string).
495
554
  */
496
555
  static VALUE
497
556
  strio_set_string(VALUE self, VALUE string)
@@ -509,10 +568,13 @@ strio_set_string(VALUE self, VALUE string)
509
568
 
510
569
  /*
511
570
  * call-seq:
512
- * strio.close -> nil
571
+ * close -> nil
572
+ *
573
+ * Closes +self+ for both reading and writing.
513
574
  *
514
- * Closes a StringIO. The stream is unavailable for any further data
515
- * operations; an +IOError+ is raised if such an attempt is made.
575
+ * Raises IOError if reading or writing is attempted.
576
+ *
577
+ * Related: StringIO#close_read, StringIO#close_write.
516
578
  */
517
579
  static VALUE
518
580
  strio_close(VALUE self)
@@ -524,10 +586,13 @@ strio_close(VALUE self)
524
586
 
525
587
  /*
526
588
  * call-seq:
527
- * strio.close_read -> nil
589
+ * close_read -> nil
590
+ *
591
+ * Closes +self+ for reading; closed-write setting remains unchanged.
592
+ *
593
+ * Raises IOError if reading is attempted.
528
594
  *
529
- * Closes the read end of a StringIO. Will raise an +IOError+ if the
530
- * receiver is not readable.
595
+ * Related: StringIO#close, StringIO#close_write.
531
596
  */
532
597
  static VALUE
533
598
  strio_close_read(VALUE self)
@@ -542,10 +607,13 @@ strio_close_read(VALUE self)
542
607
 
543
608
  /*
544
609
  * call-seq:
545
- * strio.close_write -> nil
610
+ * close_write -> nil
546
611
  *
547
- * Closes the write end of a StringIO. Will raise an +IOError+ if the
548
- * receiver is not writeable.
612
+ * Closes +self+ for writing; closed-read setting remains unchanged.
613
+ *
614
+ * Raises IOError if writing is attempted.
615
+ *
616
+ * Related: StringIO#close, StringIO#close_read.
549
617
  */
550
618
  static VALUE
551
619
  strio_close_write(VALUE self)
@@ -560,9 +628,10 @@ strio_close_write(VALUE self)
560
628
 
561
629
  /*
562
630
  * call-seq:
563
- * strio.closed? -> true or false
631
+ * closed? -> true or false
564
632
  *
565
- * Returns +true+ if the stream is completely closed, +false+ otherwise.
633
+ * Returns +true+ if +self+ is closed for both reading and writing,
634
+ * +false+ otherwise.
566
635
  */
567
636
  static VALUE
568
637
  strio_closed(VALUE self)
@@ -574,9 +643,9 @@ strio_closed(VALUE self)
574
643
 
575
644
  /*
576
645
  * call-seq:
577
- * strio.closed_read? -> true or false
646
+ * closed_read? -> true or false
578
647
  *
579
- * Returns +true+ if the stream is not readable, +false+ otherwise.
648
+ * Returns +true+ if +self+ is closed for reading, +false+ otherwise.
580
649
  */
581
650
  static VALUE
582
651
  strio_closed_read(VALUE self)
@@ -588,9 +657,9 @@ strio_closed_read(VALUE self)
588
657
 
589
658
  /*
590
659
  * call-seq:
591
- * strio.closed_write? -> true or false
660
+ * closed_write? -> true or false
592
661
  *
593
- * Returns +true+ if the stream is not writable, +false+ otherwise.
662
+ * Returns +true+ if +self+ is closed for writing, +false+ otherwise.
594
663
  */
595
664
  static VALUE
596
665
  strio_closed_write(VALUE self)
@@ -610,11 +679,14 @@ strio_to_read(VALUE self)
610
679
 
611
680
  /*
612
681
  * call-seq:
613
- * strio.eof -> true or false
614
- * strio.eof? -> true or false
682
+ * eof? -> true or false
683
+ *
684
+ * Returns +true+ if positioned at end-of-stream, +false+ otherwise;
685
+ * see {Position}[https://docs.ruby-lang.org/en/master/File.html#class-File-label-Position].
615
686
  *
616
- * Returns true if the stream is at the end of the data (underlying string).
617
- * The stream must be opened for reading or an +IOError+ will be raised.
687
+ * Raises IOError if the stream is not opened for reading.
688
+ *
689
+ * StreamIO#eof is an alias for StreamIO#eof?.
618
690
  */
619
691
  static VALUE
620
692
  strio_eof(VALUE self)
@@ -644,13 +716,10 @@ strio_copy(VALUE copy, VALUE orig)
644
716
 
645
717
  /*
646
718
  * call-seq:
647
- * strio.lineno -> integer
719
+ * lineno -> current_line_number
648
720
  *
649
- * Returns the current line number. The stream must be
650
- * opened for reading. +lineno+ counts the number of times +gets+ is
651
- * called, rather than the number of newlines encountered. The two
652
- * values will differ if +gets+ is called with a separator other than
653
- * newline. See also the <code>$.</code> variable.
721
+ * Returns the current line number in +self+;
722
+ * see {Line Number}[https://docs.ruby-lang.org/en/master/IO.html#label-Line+Number].
654
723
  */
655
724
  static VALUE
656
725
  strio_get_lineno(VALUE self)
@@ -660,10 +729,10 @@ strio_get_lineno(VALUE self)
660
729
 
661
730
  /*
662
731
  * call-seq:
663
- * strio.lineno = integer -> integer
732
+ * lineno = new_line_number -> new_line_number
664
733
  *
665
- * Manually sets the current line number to the given value.
666
- * <code>$.</code> is updated only on the next read.
734
+ * Sets the current line number in +self+ to the given +new_line_number+;
735
+ * see {Line Number}[https://docs.ruby-lang.org/en/master/IO.html#label-Line+Number].
667
736
  */
668
737
  static VALUE
669
738
  strio_set_lineno(VALUE self, VALUE lineno)
@@ -674,9 +743,10 @@ strio_set_lineno(VALUE self, VALUE lineno)
674
743
 
675
744
  /*
676
745
  * call-seq:
677
- * strio.binmode -> stringio
746
+ * binmode -> self
678
747
  *
679
- * Puts stream into binary mode. See IO#binmode.
748
+ * Sets the data mode in +self+ to binary mode;
749
+ * see {Data Mode}[https://docs.ruby-lang.org/en/master/File.html#class-File-label-Data+Mode].
680
750
  *
681
751
  */
682
752
  static VALUE
@@ -700,11 +770,27 @@ strio_binmode(VALUE self)
700
770
 
701
771
  /*
702
772
  * call-seq:
703
- * strio.reopen(other_StrIO) -> strio
704
- * strio.reopen(string, mode) -> strio
773
+ * reopen(other, mode = 'r+') -> self
774
+ *
775
+ * Reinitializes the stream with the given +other+ (string or StringIO) and +mode+;
776
+ * see IO.new:
777
+ *
778
+ * StringIO.open('foo') do |strio|
779
+ * p strio.string
780
+ * strio.reopen('bar')
781
+ * p strio.string
782
+ * other_strio = StringIO.new('baz')
783
+ * strio.reopen(other_strio)
784
+ * p strio.string
785
+ * other_strio.close
786
+ * end
787
+ *
788
+ * Output:
789
+ *
790
+ * "foo"
791
+ * "bar"
792
+ * "baz"
705
793
  *
706
- * Reinitializes the stream with the given <i>other_StrIO</i> or _string_
707
- * and _mode_ (see StringIO#new).
708
794
  */
709
795
  static VALUE
710
796
  strio_reopen(int argc, VALUE *argv, VALUE self)
@@ -718,10 +804,12 @@ strio_reopen(int argc, VALUE *argv, VALUE self)
718
804
 
719
805
  /*
720
806
  * call-seq:
721
- * strio.pos -> integer
722
- * strio.tell -> integer
807
+ * pos -> stream_position
723
808
  *
724
- * Returns the current offset (in bytes).
809
+ * Returns the current position (in bytes);
810
+ * see {Position}[https://docs.ruby-lang.org/en/master/IO.html#label-Position].
811
+ *
812
+ * StringIO#tell is an alias for StringIO#pos.
725
813
  */
726
814
  static VALUE
727
815
  strio_get_pos(VALUE self)
@@ -731,9 +819,10 @@ strio_get_pos(VALUE self)
731
819
 
732
820
  /*
733
821
  * call-seq:
734
- * strio.pos = integer -> integer
822
+ * pos = new_position -> new_position
735
823
  *
736
- * Seeks to the given position (in bytes).
824
+ * Sets the current position (in bytes);
825
+ * see {Position}[https://docs.ruby-lang.org/en/master/IO.html#label-Position].
737
826
  */
738
827
  static VALUE
739
828
  strio_set_pos(VALUE self, VALUE pos)
@@ -749,10 +838,11 @@ strio_set_pos(VALUE self, VALUE pos)
749
838
 
750
839
  /*
751
840
  * call-seq:
752
- * strio.rewind -> 0
841
+ * rewind -> 0
753
842
  *
754
- * Positions the stream to the beginning of input, resetting
755
- * +lineno+ to zero.
843
+ * Sets the current position and line number to zero;
844
+ * see {Position}[https://docs.ruby-lang.org/en/master/IO.html#label-Position]
845
+ * and {Line Number}[https://docs.ruby-lang.org/en/master/IO.html#label-Line+Number].
756
846
  */
757
847
  static VALUE
758
848
  strio_rewind(VALUE self)
@@ -765,10 +855,11 @@ strio_rewind(VALUE self)
765
855
 
766
856
  /*
767
857
  * call-seq:
768
- * strio.seek(amount, whence=SEEK_SET) -> 0
858
+ * seek(offset, whence = SEEK_SET) -> 0
769
859
  *
770
- * Seeks to a given offset _amount_ in the stream according to
771
- * the value of _whence_ (see IO#seek).
860
+ * Sets the current position to the given integer +offset+ (in bytes),
861
+ * with respect to a given constant +whence+;
862
+ * see {Position}[https://docs.ruby-lang.org/en/master/IO.html#label-Position].
772
863
  */
773
864
  static VALUE
774
865
  strio_seek(int argc, VALUE *argv, VALUE self)
@@ -804,9 +895,9 @@ strio_seek(int argc, VALUE *argv, VALUE self)
804
895
 
805
896
  /*
806
897
  * call-seq:
807
- * strio.sync -> true
898
+ * sync -> true
808
899
  *
809
- * Returns +true+ always.
900
+ * Returns +true+; implemented only for compatibility with other stream classes.
810
901
  */
811
902
  static VALUE
812
903
  strio_get_sync(VALUE self)
@@ -821,10 +912,12 @@ strio_get_sync(VALUE self)
821
912
 
822
913
  /*
823
914
  * call-seq:
824
- * strio.each_byte {|byte| block } -> strio
825
- * strio.each_byte -> anEnumerator
915
+ * each_byte {|byte| ... } -> self
916
+ *
917
+ * With a block given, calls the block with each remaining byte in the stream;
918
+ * see {Byte IO}[https://docs.ruby-lang.org/en/master/IO.html#label-Byte+IO].
826
919
  *
827
- * See IO#each_byte.
920
+ * With no block given, returns an enumerator.
828
921
  */
829
922
  static VALUE
830
923
  strio_each_byte(VALUE self)
@@ -842,9 +935,10 @@ strio_each_byte(VALUE self)
842
935
 
843
936
  /*
844
937
  * call-seq:
845
- * strio.getc -> string or nil
938
+ * getc -> character or nil
846
939
  *
847
- * See IO#getc.
940
+ * Reads and returns the next character from the stream;
941
+ * see {Character IO}[https://docs.ruby-lang.org/en/master/IO.html#label-Character+IO].
848
942
  */
849
943
  static VALUE
850
944
  strio_getc(VALUE self)
@@ -867,9 +961,10 @@ strio_getc(VALUE self)
867
961
 
868
962
  /*
869
963
  * call-seq:
870
- * strio.getbyte -> fixnum or nil
964
+ * getbyte -> byte or nil
871
965
  *
872
- * See IO#getbyte.
966
+ * Reads and returns the next 8-bit byte from the stream;
967
+ * see {Byte IO}[https://docs.ruby-lang.org/en/master/IO.html#label-Byte+IO].
873
968
  */
874
969
  static VALUE
875
970
  strio_getbyte(VALUE self)
@@ -905,12 +1000,10 @@ strio_extend(struct StringIO *ptr, long pos, long len)
905
1000
 
906
1001
  /*
907
1002
  * call-seq:
908
- * strio.ungetc(string) -> nil
1003
+ * ungetc(character) -> nil
909
1004
  *
910
- * Pushes back one character (passed as a parameter)
911
- * such that a subsequent buffered read will return it. There is no
912
- * limitation for multiple pushbacks including pushing back behind the
913
- * beginning of the buffer string.
1005
+ * Pushes back ("unshifts") a character or integer onto the stream;
1006
+ * see {Character IO}[https://docs.ruby-lang.org/en/master/IO.html#label-Character+IO].
914
1007
  */
915
1008
  static VALUE
916
1009
  strio_ungetc(VALUE self, VALUE c)
@@ -945,9 +1038,10 @@ strio_ungetc(VALUE self, VALUE c)
945
1038
 
946
1039
  /*
947
1040
  * call-seq:
948
- * strio.ungetbyte(fixnum) -> nil
1041
+ * ungetbyte(byte) -> nil
949
1042
  *
950
- * See IO#ungetbyte
1043
+ * Pushes back ("unshifts") an 8-bit byte onto the stream;
1044
+ * see {Byte IO}[https://docs.ruby-lang.org/en/master/IO.html#label-Byte+IO].
951
1045
  */
952
1046
  static VALUE
953
1047
  strio_ungetbyte(VALUE self, VALUE c)
@@ -984,7 +1078,7 @@ strio_unget_bytes(struct StringIO *ptr, const char *cp, long cl)
984
1078
  len = RSTRING_LEN(str);
985
1079
  rest = pos - len;
986
1080
  if (cl > pos) {
987
- long ex = (rest < 0 ? cl-pos : cl+rest);
1081
+ long ex = cl - (rest < 0 ? pos : len);
988
1082
  rb_str_modify_expand(str, ex);
989
1083
  rb_str_set_len(str, len + ex);
990
1084
  s = RSTRING_PTR(str);
@@ -1007,9 +1101,10 @@ strio_unget_bytes(struct StringIO *ptr, const char *cp, long cl)
1007
1101
 
1008
1102
  /*
1009
1103
  * call-seq:
1010
- * strio.readchar -> string
1104
+ * readchar -> string
1011
1105
  *
1012
- * See IO#readchar.
1106
+ * Like +getc+, but raises an exception if already at end-of-stream;
1107
+ * see {Character IO}[https://docs.ruby-lang.org/en/master/IO.html#label-Character+IO].
1013
1108
  */
1014
1109
  static VALUE
1015
1110
  strio_readchar(VALUE self)
@@ -1021,9 +1116,10 @@ strio_readchar(VALUE self)
1021
1116
 
1022
1117
  /*
1023
1118
  * call-seq:
1024
- * strio.readbyte -> fixnum
1119
+ * readbyte -> byte
1025
1120
  *
1026
- * See IO#readbyte.
1121
+ * Like +getbyte+, but raises an exception if already at end-of-stream;
1122
+ * see {Byte IO}[https://docs.ruby-lang.org/en/master/IO.html#label-Byte+IO].
1027
1123
  */
1028
1124
  static VALUE
1029
1125
  strio_readbyte(VALUE self)
@@ -1035,10 +1131,12 @@ strio_readbyte(VALUE self)
1035
1131
 
1036
1132
  /*
1037
1133
  * call-seq:
1038
- * strio.each_char {|char| block } -> strio
1039
- * strio.each_char -> anEnumerator
1134
+ * each_char {|c| ... } -> self
1135
+ *
1136
+ * With a block given, calls the block with each remaining character in the stream;
1137
+ * see {Character IO}[https://docs.ruby-lang.org/en/master/IO.html#label-Character+IO].
1040
1138
  *
1041
- * See IO#each_char.
1139
+ * With no block given, returns an enumerator.
1042
1140
  */
1043
1141
  static VALUE
1044
1142
  strio_each_char(VALUE self)
@@ -1055,10 +1153,12 @@ strio_each_char(VALUE self)
1055
1153
 
1056
1154
  /*
1057
1155
  * call-seq:
1058
- * strio.each_codepoint {|c| block } -> strio
1059
- * strio.each_codepoint -> anEnumerator
1156
+ * each_codepoint {|codepoint| ... } -> self
1060
1157
  *
1061
- * See IO#each_codepoint.
1158
+ * With a block given, calls the block with each remaining codepoint in the stream;
1159
+ * see {Codepoint IO}[https://docs.ruby-lang.org/en/master/IO.html#label-Codepoint+IO].
1160
+ *
1161
+ * With no block given, returns an enumerator.
1062
1162
  */
1063
1163
  static VALUE
1064
1164
  strio_each_codepoint(VALUE self)
@@ -1125,8 +1225,10 @@ prepare_getline_args(struct getline_arg *arg, int argc, VALUE *argv)
1125
1225
  {
1126
1226
  VALUE str, lim, opts;
1127
1227
  long limit = -1;
1228
+ int respect_chomp;
1128
1229
 
1129
1230
  argc = rb_scan_args(argc, argv, "02:", &str, &lim, &opts);
1231
+ respect_chomp = argc == 0 || !NIL_P(str);
1130
1232
  switch (argc) {
1131
1233
  case 0:
1132
1234
  str = rb_rs;
@@ -1160,7 +1262,9 @@ prepare_getline_args(struct getline_arg *arg, int argc, VALUE *argv)
1160
1262
  keywords[0] = rb_intern_const("chomp");
1161
1263
  }
1162
1264
  rb_get_kwargs(opts, keywords, 0, 1, &vchomp);
1163
- arg->chomp = (vchomp != Qundef) && RTEST(vchomp);
1265
+ if (respect_chomp) {
1266
+ arg->chomp = (vchomp != Qundef) && RTEST(vchomp);
1267
+ }
1164
1268
  }
1165
1269
  return arg;
1166
1270
  }
@@ -1181,7 +1285,7 @@ strio_getline(struct getline_arg *arg, struct StringIO *ptr)
1181
1285
  const char *s, *e, *p;
1182
1286
  long n, limit = arg->limit;
1183
1287
  VALUE str = arg->rs;
1184
- int w = 0;
1288
+ long w = 0;
1185
1289
  rb_encoding *enc = get_enc(ptr);
1186
1290
 
1187
1291
  if (ptr->pos >= (n = RSTRING_LEN(ptr->string))) {
@@ -1200,6 +1304,7 @@ strio_getline(struct getline_arg *arg, struct StringIO *ptr)
1200
1304
  str = strio_substr(ptr, ptr->pos, e - s - w, enc);
1201
1305
  }
1202
1306
  else if ((n = RSTRING_LEN(str)) == 0) {
1307
+ const char *paragraph_end = NULL;
1203
1308
  p = s;
1204
1309
  while (p[(p + 1 < e) && (*p == '\r') && 0] == '\n') {
1205
1310
  p += *p == '\r';
@@ -1209,19 +1314,21 @@ strio_getline(struct getline_arg *arg, struct StringIO *ptr)
1209
1314
  }
1210
1315
  s = p;
1211
1316
  while ((p = memchr(p, '\n', e - p)) && (p != e)) {
1212
- if (*++p == '\n') {
1213
- e = p + 1;
1214
- w = (arg->chomp ? 1 : 0);
1215
- break;
1216
- }
1217
- else if (*p == '\r' && p < e && p[1] == '\n') {
1218
- e = p + 2;
1219
- w = (arg->chomp ? 2 : 0);
1220
- break;
1221
- }
1317
+ p++;
1318
+ if (!((p < e && *p == '\n') ||
1319
+ (p + 1 < e && *p == '\r' && *(p+1) == '\n'))) {
1320
+ continue;
1321
+ }
1322
+ paragraph_end = p - ((*(p-2) == '\r') ? 2 : 1);
1323
+ while ((p < e && *p == '\n') ||
1324
+ (p + 1 < e && *p == '\r' && *(p+1) == '\n')) {
1325
+ p += (*p == '\r') ? 2 : 1;
1326
+ }
1327
+ e = p;
1328
+ break;
1222
1329
  }
1223
- if (!w && arg->chomp) {
1224
- w = chomp_newline_width(s, e);
1330
+ if (arg->chomp && paragraph_end) {
1331
+ w = e - paragraph_end;
1225
1332
  }
1226
1333
  str = strio_substr(ptr, s - RSTRING_PTR(ptr->string), e - s - w, enc);
1227
1334
  }
@@ -1237,7 +1344,8 @@ strio_getline(struct getline_arg *arg, struct StringIO *ptr)
1237
1344
  if (e - s < 1024) {
1238
1345
  for (p = s; p + n <= e; ++p) {
1239
1346
  if (MEMCMP(p, RSTRING_PTR(str), char, n) == 0) {
1240
- e = p + (arg->chomp ? 0 : n);
1347
+ e = p + n;
1348
+ w = (arg->chomp ? n : 0);
1241
1349
  break;
1242
1350
  }
1243
1351
  }
@@ -1260,11 +1368,13 @@ strio_getline(struct getline_arg *arg, struct StringIO *ptr)
1260
1368
 
1261
1369
  /*
1262
1370
  * call-seq:
1263
- * strio.gets(sep=$/, chomp: false) -> string or nil
1264
- * strio.gets(limit, chomp: false) -> string or nil
1265
- * strio.gets(sep, limit, chomp: false) -> string or nil
1371
+ * gets(sep = $/, chomp: false) -> string or nil
1372
+ * gets(limit, chomp: false) -> string or nil
1373
+ * gets(sep, limit, chomp: false) -> string or nil
1266
1374
  *
1267
- * See IO#gets.
1375
+ * Reads and returns a line from the stream;
1376
+ * assigns the return value to <tt>$_</tt>;
1377
+ * see {Line IO}[https://docs.ruby-lang.org/en/master/IO.html#label-Line+IO].
1268
1378
  */
1269
1379
  static VALUE
1270
1380
  strio_gets(int argc, VALUE *argv, VALUE self)
@@ -1284,11 +1394,12 @@ strio_gets(int argc, VALUE *argv, VALUE self)
1284
1394
 
1285
1395
  /*
1286
1396
  * call-seq:
1287
- * strio.readline(sep=$/, chomp: false) -> string
1288
- * strio.readline(limit, chomp: false) -> string or nil
1289
- * strio.readline(sep, limit, chomp: false) -> string or nil
1397
+ * readline(sep = $/, chomp: false) -> string
1398
+ * readline(limit, chomp: false) -> string
1399
+ * readline(sep, limit, chomp: false) -> string
1290
1400
  *
1291
- * See IO#readline.
1401
+ * Reads a line as with IO#gets, but raises EOFError if already at end-of-file;
1402
+ * see {Line IO}[https://docs.ruby-lang.org/en/master/IO.html#label-Line+IO].
1292
1403
  */
1293
1404
  static VALUE
1294
1405
  strio_readline(int argc, VALUE *argv, VALUE self)
@@ -1300,17 +1411,16 @@ strio_readline(int argc, VALUE *argv, VALUE self)
1300
1411
 
1301
1412
  /*
1302
1413
  * call-seq:
1303
- * strio.each(sep=$/, chomp: false) {|line| block } -> strio
1304
- * strio.each(limit, chomp: false) {|line| block } -> strio
1305
- * strio.each(sep, limit, chomp: false) {|line| block } -> strio
1306
- * strio.each(...) -> anEnumerator
1414
+ * each_line(sep = $/, chomp: false) {|line| ... } -> self
1415
+ * each_line(limit, chomp: false) {|line| ... } -> self
1416
+ * each_line(sep, limit, chomp: false) {|line| ... } -> self
1307
1417
  *
1308
- * strio.each_line(sep=$/, chomp: false) {|line| block } -> strio
1309
- * strio.each_line(limit, chomp: false) {|line| block } -> strio
1310
- * strio.each_line(sep, limit, chomp: false) {|line| block } -> strio
1311
- * strio.each_line(...) -> anEnumerator
1418
+ * Calls the block with each remaining line read from the stream;
1419
+ * does nothing if already at end-of-file;
1420
+ * returns +self+.
1421
+ * See {Line IO}[https://docs.ruby-lang.org/en/master/IO.html#label-Line+IO].
1312
1422
  *
1313
- * See IO#each.
1423
+ * StringIO#each is an alias for StringIO#each_line.
1314
1424
  */
1315
1425
  static VALUE
1316
1426
  strio_each(int argc, VALUE *argv, VALUE self)
@@ -1655,7 +1765,7 @@ strio_truncate(VALUE self, VALUE len)
1655
1765
  if (plen < l) {
1656
1766
  MEMZERO(RSTRING_PTR(string) + plen, char, l - plen);
1657
1767
  }
1658
- return len;
1768
+ return INT2FIX(0);
1659
1769
  }
1660
1770
 
1661
1771
  /*
@@ -1711,7 +1821,14 @@ strio_set_encoding(int argc, VALUE *argv, VALUE self)
1711
1821
  enc = rb_default_external_encoding();
1712
1822
  }
1713
1823
  else {
1714
- enc = rb_to_encoding(ext_enc);
1824
+ enc = rb_find_encoding(ext_enc);
1825
+ if (!enc) {
1826
+ struct rb_io_enc_t convconfig;
1827
+ int oflags, fmode;
1828
+ VALUE vmode = rb_str_append(rb_str_new_cstr("r:"), ext_enc);
1829
+ rb_io_extract_modeenc(&vmode, 0, Qnil, &oflags, &fmode, &convconfig);
1830
+ enc = convconfig.enc2;
1831
+ }
1715
1832
  }
1716
1833
  ptr->enc = enc;
1717
1834
  if (WRITABLE(self)) {
@@ -1731,24 +1848,16 @@ strio_set_encoding_by_bom(VALUE self)
1731
1848
  }
1732
1849
 
1733
1850
  /*
1734
- * Pseudo I/O on String object, with interface corresponding to IO.
1851
+ * \IO streams for strings, with access similar to
1852
+ * {IO}[https://docs.ruby-lang.org/en/master/IO.html];
1853
+ * see {IO}[https://docs.ruby-lang.org/en/master/IO.html].
1735
1854
  *
1736
- * Commonly used to simulate <code>$stdio</code> or <code>$stderr</code>
1855
+ * === About the Examples
1737
1856
  *
1738
- * === Examples
1857
+ * Examples on this page assume that \StringIO has been required:
1739
1858
  *
1740
1859
  * require 'stringio'
1741
1860
  *
1742
- * # Writing stream emulation
1743
- * io = StringIO.new
1744
- * io.puts "Hello World"
1745
- * io.string #=> "Hello World\n"
1746
- *
1747
- * # Reading stream emulation
1748
- * io = StringIO.new "first\nsecond\nlast\n"
1749
- * io.getc #=> "f"
1750
- * io.gets #=> "irst\n"
1751
- * io.read #=> "second\nlast\n"
1752
1861
  */
1753
1862
  void
1754
1863
  Init_stringio(void)
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: stringio
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.0.2
4
+ version: 3.0.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Nobu Nakada
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2022-05-09 00:00:00.000000000 Z
12
+ date: 2022-12-08 00:00:00.000000000 Z
13
13
  dependencies: []
14
14
  description: Pseudo `IO` class from/to `String`.
15
15
  email:
@@ -43,7 +43,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
43
43
  - !ruby/object:Gem::Version
44
44
  version: '2.6'
45
45
  requirements: []
46
- rubygems_version: 3.3.7
46
+ rubygems_version: 3.3.26
47
47
  signing_key:
48
48
  specification_version: 4
49
49
  summary: Pseudo IO on String