Hi Rich,

I remember we met several times @internal meetings and @Devcon / Summit.
The common branch of M and MV might be The Ubiquitous B-Tree - 1979 by Dougles Comer.
On the other hand mid 60ties it was time to have something new to support creative and faster development.
So they might quite well taken ideas from each other.
So as you find many lingual constructs that are pretty similar to Java.
Don Nelson didn't pass my way. But I have a personal gap from '85 to '99 where I was on a complete different road.

You are right. We were happy writing a whole operating system in Assembly language (VAX/MACRO32) and we found it partially overdone compared to PDP-11/MACRO16. But we knew exactly what every bit in our box did. Not even C could give us that level of control.

I personally think a programming language reaches its limits when only a low percentage of developers still oversee it.
Therefore I think your idea to have a new layer on top of COS is much better as it doesn't impose any limitations that are required for backward compatibility.
So you are free to take with you what seems useful and leave behind old junk.

COS contains a real bad example that causes troubles over and over for beginners:
IF  / ELSE old style manipulating $T   vs.   IF { } ELSE { } new style not touching $T 
and some others

That must no happen again. With a new layer you leave this behind and have all freedom.

Maks I fully support your position.
There are very few languages where you can run code written  40 yrs. ago with no modification !
That's what counts for customers.

You have other languages in parallel like MV or BASIC besides all the embedded things like &SQL(), &HTML(), &JS()..

But with same reasoning you may ask why is Java, JavaScript  or C, C# not changed?
Because you got GO, Angular, ..... to have attractive extensions.
COS has it's ZZ*, $ZZ* as extensions.  ( ZZ* ! )

Isn't this enough for thousands of developers that haven't asked for it nor have a need  for it?  

if you open BPL in Studio click here to switch to Class view

by program the code is found in class %Dictionary.XDataDefinition

Property Data holds your XData as Stream

http://docs.intersystems.com/latest/csp/documatic/%25CSP.Documatic.cls?P...

to find the id you can use
select ID from %Dictionary.XDataDefinition where parent %startswith '<my class name>'

for this cases a possible solution could be 

%Stream.Global has a FindAt method that could give you a position of  "\u00"

[Find the first occurrence of target in the stream starting the search at position. ]

http://docs.intersystems.com/latest/csp/documatic/%25CSP.Documatic.cls?P...

But: if you are on the decoded stream all non printables are just single characters. No issue to cut it in pieces

  • read your source stream in reasonable sized junks
  • clean out what ever you need
  • append it to a temporary stream
  • loop on source until you hit AtEnd condition
  • finally replace your source either by "copyFromSteam" method [temp -> source]
    or replace source stream reference by temp stream reference

I guess the whole code is shorter than this description.

I'd suggest not to touch the global under the source steam.

The default for %String is MAXLEN=50

if you write in your definition %String(MAXLEN="")   also in Method calls this should be enough.

Query Methode(data1 As %Library.String(MAXLEN=""), data2 As %Library.String(MAXLEN=""), data3 As %Library.String(MAXLEN="")) As %Library.Query(CONTAINID = 1, ROWSPEC = "Result,Par2:%String") [ SqlProc ]

  and so on.

Or you make you own data type  inheriting %String overwriting  Parameter MAXLEN=""

Or just use %Library.VarString which makes just this MAXLEN=""
http://docs.intersystems.com/latest/csp/documatic/%25CSP.Documatic.cls?P...

Query Methode(data1 As %LibraryVar.String, data2 As %Library.VarString, data3 As %Library.VarString) As %Library.Query(CONTAINID = 1, ROWSPEC = "Result,Par2:%VarString") [ SqlProc ]

  and so on.

of course it makes sense!

but then you know which application is using it and can use the application's cleaning method / routine that takes care of all kind of dependencies:
I remember well times when routines used to start with  KILL ^CacheTemp*($JOB)
I expected over time most applications are using PPG  (^||myGlobal...) to avoid this. Or have a Clean-Up.