Clip, a command line clipboard handler. Source code included.
A note about the future of ecsoft2.org
ecsoft2.org runs on software (Drupal 7 and PHP 7.4) that reached its end of life years ago and no longer receives security updates. Keeping the site online safely is getting harder.
Giving it a future means migrating it to a current platform — and that is only worth doing if people still use it and want to help keep it alive.
If you care about ecsoft2.org, as a user, a contributor, or someone willing to lend a hand, please ggamba
tiscali [dot] it (get in touch) by January 31, 2027.
If no one comes forward by then, the site will be turned into a read-only archive, so that its content stays available.
Program is distributed as ZIP package: download to temporary directory and unpack to destination folder, better if in PATH. See below for download link(s).
Following ones are the download links for manual installation:
| Clip v. 0.1 (10/10/2014, Sergey I. Yevtushenko) | Readme/What's new |
From: Sergey I. Yevtushenko
Newsgroups: comp.os.os2.programmer.misc
Subject: Clipboard utility
Date: 15 Feb 2000 09:51:36 GMT
Organization: ES@Home
Lines: 387
Message-ID: <0Wpe3JvzLE6N-pn2-NLd5ds68ZFNw@sweethome>
NNTP-Posting-Host: ppp-160.nav.kiev.ua
Mime-Version: 1.0
Content-Type: text/plain; charset="koi8-r"
Content-Transfer-Encoding: 8bit
X-Trace: gateway.nav.kiev.ua 950608296 21671 (None) 193.193.197.160
X-Complaints-To: newsmaster@gateway.nav.kiev.ua
X-Newsreader: ProNews/2 Version 1.50ß1
Path: news2.prserv.net!newsfeed2.us.ibm.net!ibm.net!news-spur1.maxwell.syr.edu!news.maxwell.syr.edu!logbridge.uoregon.edu!nntp.upenn.edu!news.myxa.com!iad-feed.news.verio.net!carrier.kiev.ua!nav.kiev.ua!not-for-mail
Xref: news2.prserv.net comp.os.os2.programmer.misc:58256
Hello,
Below is an source code of utility for accessing clipboard from command line.
It allows to put data from stdin to clipboard and print clipboard content
to the stdout.
It automatically detects that STDIN (STDOUT) is pipe or file
and chooses appropriate mode. Each mode can be forced to allow
program to work with character devices (console/COMx/etc).
Because modes are not exclusive, it is possible to put this utility
in the mid of pipe and get pipe content mirrored in clipboard.
Examples:
1. Program output to clipboard:
[C:\]dir | clip
2. Clipboard to program output:
[C:\]clip | more
3. Pipe between programs:
[C:\]dir | clip | more
4. Force stdin:
[C:\]clip -i
type> Some test string
^Z
5. Force stdout:
[C:\]clip -o
Some test string
Hope it will be useful not only for me :-)
Comments and suggestions are welcome.
Compile with VAC++ 3.08:
icc -O+ -Oc+ -Ss+ -Gs+ -Gl+ -G5 -Q+ -Gm+ -B"/ST:32768 /NOE /E:2" clip.cpp
Compile with WATCOM C++ 10.6:
wcl386 -oneatx clip.cpp
Simple command line for both compilers works too:
icc clip.cpp
wcl386 clip.cpp
----------- cut -----------
/*
** Module :CLIP.CPP
** Abstract :Clipboard command line utility
**
** Public domain by Sergey I. Yevtushenko
**
** Log: Tue 15/02/2000 Created
**
*/
#define INCL_DOS
#define INCL_WIN
#include <os2.h>
#include <stdio.h>
#include <string.h>
#define MODE_NONE 0
#define MODE_IN 0x0001
#define MODE_OUT 0x0002
struct Chunk
{
Chunk *next;
int sz;
char data[2048];
Chunk():next(0), sz(0) {}
};
BOOL (APIENTRY *_inCloseClipbrd)(HAB);
HMQ (APIENTRY *_inCreateMsgQueue)(HAB, LONG);
BOOL (APIENTRY *_inDestroyMsgQueue)(HMQ);
BOOL (APIENTRY *_inEmptyClipbrd)(HAB);
HAB (APIENTRY *_inInitialize)(ULONG);
BOOL (APIENTRY *_inOpenClipbrd)(HAB);
ULONG(APIENTRY *_inQueryClipbrdData)(HAB, ULONG);
BOOL (APIENTRY *_inQueryClipbrdFmtInfo)(HAB, ULONG, PULONG);
BOOL (APIENTRY *_inSetClipbrdData)(HAB, ULONG, ULONG, ULONG);
BOOL (APIENTRY *_inTerminate)(HAB);
HAB hab;
HMQ hmq;
//---------------------------------------------------------------
// STDIN Stuff
//---------------------------------------------------------------
char *ReadPipe(int iPipe)
{
APIRET rc;
ULONG ulTotal = 0;
ULONG ulBytesRead = 0;
Chunk* pHead = new Chunk;
Chunk* pCurr = pHead;
do
{
ulBytesRead = 0;
rc = DosRead(0, pCurr->data, sizeof(pCurr->data), &ulBytesRead);
pCurr->sz = ulBytesRead;
ulTotal += ulBytesRead;
if(ulBytesRead)
{
pCurr->next = new Chunk;
pCurr = pCurr->next;
}
}
while(!rc && ulBytesRead);
char *str = 0;
if(ulTotal)
{
str = new char[ulTotal+1];
char *ptr = str;
for(pCurr = pHead; pCurr; pCurr = pCurr->next)
{
if(!pCurr->sz)
continue;
memcpy(ptr, pCurr->data, pCurr->sz);
ptr += pCurr->sz;
}
*ptr = 0;
}
//Free memory
for(pCurr = pHead; pCurr; )
{
Chunk* pTmp = pCurr;
pCurr = pCurr->next;
delete pTmp;
}
return str;
}
//---------------------------------------------------------------
// PM Stuff
//---------------------------------------------------------------
int init_pm(void)
{
PPIB pib;
PTIB tib;
APIRET rc;
HMODULE hMte = 0;
char loadErr[256];
if(hab || hmq)
return 0;
rc = DosGetInfoBlocks(&tib, &pib);
rc = DosQueryModuleHandle("PMWIN", &hMte);
if(rc)
return 1;
pib->pib_ultype = 3;
rc = DosLoadModule(loadErr, sizeof(loadErr), "PMWIN", &hMte);
if(rc)
return 1;
rc = DosQueryProcAddr(hMte, 707, 0, (PFN*)&_inCloseClipbrd);
rc = DosQueryProcAddr(hMte, 716, 0, (PFN*)&_inCreateMsgQueue);
rc = DosQueryProcAddr(hMte, 726, 0, (PFN*)&_inDestroyMsgQueue);
rc = DosQueryProcAddr(hMte, 733, 0, (PFN*)&_inEmptyClipbrd);
rc = DosQueryProcAddr(hMte, 763, 0, (PFN*)&_inInitialize);
rc = DosQueryProcAddr(hMte, 793, 0, (PFN*)&_inOpenClipbrd);
rc = DosQueryProcAddr(hMte, 806, 0, (PFN*)&_inQueryClipbrdData);
rc = DosQueryProcAddr(hMte, 807, 0, (PFN*)&_inQueryClipbrdFmtInfo);
rc = DosQueryProcAddr(hMte, 854, 0, (PFN*)&_inSetClipbrdData);
rc = DosQueryProcAddr(hMte, 888, 0, (PFN*)&_inTerminate);
hab = _inInitialize(0);
hmq = _inCreateMsgQueue(hab, 0);
return 0;
}
void done_pm(void)
{
if(hmq)
_inDestroyMsgQueue(hmq);
if(hab)
_inTerminate(hab);
hab = 0;
hmq = 0;
}
void set_clip(char *text)
{
if(!hab || !text)
return;
char *pByte = 0;
//Calculate size of buffer
int sz = strlen(text) + 1;
int i;
_inOpenClipbrd(hab);
_inEmptyClipbrd(hab);
if (!DosAllocSharedMem((PPVOID)&pByte, 0, sz,
PAG_WRITE | PAG_COMMIT | OBJ_GIVEABLE | OBJ_GETTABLE))
{
memcpy(pByte, text, sz);
_inSetClipbrdData(hab, (ULONG) pByte, CF_TEXT, CFI_POINTER);
}
_inCloseClipbrd(hab);
}
char* get_clip(void)
{
if(!hab)
return 0;
char *ClipData;
ULONG ulFormat;
_inQueryClipbrdFmtInfo(hab, CF_TEXT, &ulFormat);
if(ulFormat != CFI_POINTER)
return 0;
_inOpenClipbrd(hab);
ClipData = (char *)_inQueryClipbrdData(hab, CF_TEXT);
if(!ClipData)
return 0;
int sz = strlen(ClipData) + 1;
char *str = new char[sz];
memcpy(str, ClipData, sz);
_inCloseClipbrd(hab);
return str;
}
char cUsage[] = "CLIP V0.1 Command line clipboard handler.\r\n"
"Copyright (C) 2000 Sergey I. Yevtushenko.\r\n"
"\r\n"
"Usage: CLIP [-o[-]] [-i[-]] [-{h|?}] \r\n"
;
void usage(void)
{
ULONG ulWrote = 0;
DosWrite(1, cUsage, sizeof(cUsage) - 1, &ulWrote);
}
int main(int argc, char **argv)
{
ULONG ulType = 0;
ULONG ulAttr = 0;
APIRET rc;
int i;
int iMode = MODE_NONE;
rc = DosQueryHType(0, &ulType, &ulAttr); //STDIN
if(!rc)
{
ulType &= 0xFF;
if(ulType == 0 || ulType == 2) //file or pipe
iMode |= MODE_IN;
}
rc = DosQueryHType(1, &ulType, &ulAttr); //STDOUT
if(!rc)
{
ulType &= 0xFF;
if(ulType == 0 || ulType == 2) //file or pipe
iMode |= MODE_OUT;
}
for(i = 1; i < argc; i++)
{
if(argv[i][0] == '-' || argv[i][0] == '/')
{
switch(argv[i][1])
{
case 'I':
case 'i':
if(argv[i][2] == '-')
iMode &= ~MODE_IN;
else
iMode |= MODE_IN;
break;
case 'o':
case 'O':
if(argv[i][2] == '-')
iMode &= ~MODE_OUT;
else
iMode |= MODE_OUT;
break;
case 'h':
case 'H':
case '?':
usage();
return 0;
}
}
}
if(!iMode)
{
usage();
return 0;
}
rc = init_pm();
if(rc)
return -1;
if(iMode & MODE_IN)
{
char *str = ReadPipe(0);
if(str)
set_clip(str);
delete str;
}
if(iMode & MODE_OUT)
{
char *str = get_clip();
if(str)
{
ULONG ulWrote = 0;
rc = DosWrite(1, str, strlen(str), &ulWrote);
}
}
done_pm();
return rc;
}
----------- cut -----------
Regards,
Sergey.
*--------------------------------------
ES@Home |
hobbes.nmsu.edu/download/pub/os2/util/clipbrd/clip01.zip |

This work is licensed under a Creative Commons Attribution 4.0 International License.
Add new comment