Friday, July 26, 2013

Create and Shrink PDFs on Mac OS X

The Quartz filters that Preview uses to shrink images/PDFs sucks. But you can fix it!

Basically, just copy and edit /System/Library/Filters/Reduce File Size.qfilter, changing the compression and maxImageSize parameters. Here's the article I followed:
http://www.macworld.com/article/1168311/shrink_preview_files_without_ruining_image_quality.html

Thursday, May 16, 2013

GitHub private repository with Coda2

Coda2 does not ask for a username when adding a Git repository; if you use a private repository on GitHub, you must add it to the URL. Copy your repo's HTTPS URL from GitHub, and add 'username@' between 'https://' and 'github.com'. Example:

URL:  https://coty@github.com/coty/coolreponame.git

Wednesday, May 8, 2013

lvm saved my media organization

I had decent media organization until all my drives got full. Now finding a new TV show episode requires looking in 4 potential places, and my fstab is looking convoluted. Upgrading my server gave me the right opportunity to switch to lvm. Current server is 'stolen' and new server is 'Jupiter'.

On Jupiter:
coty@Jupiter:~$ sudo -i
root@Jupiter:~# apt-get install lvm2
root@Jupiter:~# mkdir /mnt/media
root@Jupiter:~# lvm
lvm> pvcreate /dev/sdb1 /dev/sdc1
lvm> vgcreate vg /dev/sdb1 /dev/sdc1
lvm> lvcreate -l 100%FREE -n media vg
lvm> exit
root@Jupiter:~# mkfs.ext4 /dev/vg/media
root@Jupiter:~# mount /dev/vg/media /mnt/media
//root@Jupiter:~# echo '/mnt/media 10.10.10.0/24(rw,async,subtree_check,wdelay)' >> /etc/exports
//root@Jupiter:~# mkdir /etc/exports.d
//root@Jupiter:~# service nfs-kernel-server restart
vi /etc/default/rsync
set RSYNC_ENABLE=true
vi /etc/rsyncd.conf

#motd file = /etc/rsyncd.motd
log file = /var/log/rsyncd.log
pid file = /var/run/rsyncd.pid
lock file = /var/run/rsync.lock

[media]
path = /mnt/media
#comment = My Very Own Rsync Server
#uid = nobody
#gid = nobody
read only = no
list = yes
#auth users = username
#secrets file = /etc/rsyncd.scrt


On stolen:
//mount 10.10.10.115:/mnt/media /mnt/Jupiter

Adding drives to LVM and resizing volume

/dev/sdg1, /dev/sdf1 are 1.5TB drives. /dev/sdf1 is full, /dev/sdg1 is almost full. Move a bunch of stuff off of /dev/sdg1, resize it, make a partiton, add it to the lvm pool, move more stuff off...

Resize /dev/sdg1 to the minimum partition size:
resize2fs -M /dev/sdg1

Make the new partition from free space:
cfdisk /dev/sdg1

Add it to the pool:
pvcreate /dev/sdg2
vgextend /dev/sdg2
lvextend -l 100%vg /dev/vg/media

Increase the pool partition size to maximum:
resize2fs /dev/vg/media

Cisco IOS break sequence on Mac OS X using USB to serial adapter

I'm using a USB-to-serial adapter with a Prolific 2303 chipset on my Mac with Mountain Lion to reset a Cisco router.

open source Prolific 2303 USB driver
OEM Prolific 2303 USB driver

After you install either of the drivers on your Mac, it will show up as a device in '/dev/'. Search for it:
ls /dev/tty.*

Mine was '/dev/tty.usbserial'. Connect to that device using 'screen' with 9600 serial port speed:
screen /dev/tty.usbserial 9600

Your terminal should now be connected to the serial port.

Boot your Cisco router into ROMMON by power cycling it and then entering the break sequence before it starts to boot IOS - this is usually within the first 20 or 30 seconds of booting. Some newer Cisco routers don't display anything to the serial console until after this time window. So, enter the break sequence after you turn your router on and before IOS loads. Press it multiple times as soon as power is applied to the router to try to catch it at the right time. There are two good methods:

1. For the 'screen' program that comes with OS X: CTRL-A, CTRL-B
That is, CTRL-a followed by CTRL-b. Shift is not required. CTRL-A breaks the keyboard control out of what screen is showing you, allowing you to then enter a keyboard command that screen will process instead of sending it to your serial connection. CTRL-B is a screen command to send the serial break sequence to your serial connection.

2. Reconnect screen with a serial port speed of 1200, power on the router, then press and hold the space bar for 20-30 second (or up to a minute to be safe). screen's output will not be normal while connected at this speed, and this is normal. Reconnect screen with the correct speed (the default is 9600) and press enter - you should be looking at a Rommon 2> prompt.

If you made it into ROMMON, you can change the way that the router boots up with the 'confreg' command. Run it without arguments to get a question-answer style menu you can step through, or if you just want it to boot without reading the config file (factory reset):
confreg 2142

Power cycle the router again and you should be looking at the factory IOS bootup. When you get to the prompt, use 'enable', then 'configure terminal', then 'config-register 0x2102'. This will make the router boot normally, using the config file. You will need to 'write memory' if you want the new factory default config you have to be there when you reboot.

Terminal to Serial/USB Devices From a Mac
Cisco's Break Sequence List
Send break sequence on a Cisco reverse terminal server

Wednesday, May 1, 2013

'no relaying allowed' email errors on OS X - mDNSResponder

Today I'm receiving mail delivery failures when I send email to some domains from Outlook on my Mac. It was mDNSResponder's fault.

Email:

Reporting-MTA: dns; rcdn-iport-6.cisco.com

Final-Recipient: rfc822;recipient@domain.com
Action: failed
Status: 5.0.0 (permanent failure)
Remote-MTA: dns; [123.12.34.56]
Diagnostic-Code: smtp; 5.1.0 - Unknown address error 554-'No relaying allowed - psmtp' (delivery attempts: 0)


And the solution - restart mDNSResponder from the command line (Terminal):

sudo killall mDNSResponder

Tuesday, April 16, 2013

Photoshop Scripting with Javascript

Photoshop has a couple of kinds of automation, and today I learned about scripting it with Javascript. You can also record actions into macros in the Actions toolbox/window; though these are somewhat limited, they can be assigned a hotkey from a short range of the function keys (F2, F3, etc.)

Here's the script I threw together from examples and experimenting. Its purpose is to visibly watermark a folder of images with one image. It prompts you to choose a folder of images that you want to modify, then an output folder, then the watermark image you want pasted onto the images from the folder. At each image, the script prompts you to specify which corner of the image you want the watermark on.

 /*   
 Description:  
 This script pastes one image to the chosen corner of each image in a folder.  
 */  
 // enable double clicking from the   
 // Macintosh Finder or the Windows Explorer  
 #target photoshop  
 ////////////////////////////////////  
 /// Options and Variables  
 ///  
 ////////////////////////////////////  
   
 //margin is the number of pixels you want to space the edge of the watermark  
 //from the edge of the image  
 var marginX = 5;   
 var marginY = 5;  
   
 //save a copy of the modified images to a jpeg file   
 var fileSaveOptions = new JPEGSaveOptions();  
 fileSaveOptions.embedColorProfile = true;  
 fileSaveOptions.formatOptions = FormatOptions.STANDARDBASELINE;  
 fileSaveOptions.matte = MatteType.NONE;  
 fileSaveOptions.quality = 10;  
   
 // Close the file without saving  
 var documentCloseOptions = SaveOptions.DONOTSAVECHANGES;  
                  
 // Make Photoshop the frontmost application  
 // in case we double clicked the file  
 app.bringToFront();  
   
 /////////////////////////  
 // SETUP  
 /////////////////////////  
   
 // A list of file extensions to skip, keep them lower case  
 gFilesToSkip = Array( "db", "xmp", "xcf", "thm", "txt", "doc", "md0", "tb0", "adobebridgedb", "adobebridgedbt", "bc", "bct" );  
   
 /////////////////////////  
 // MAIN  
 /////////////////////////  
   
 // Pops open a dialog for the user to  
 // choose the folder of documents to process  
 var inputFolder = Folder.selectDialog("Select a folder of documents to process");  
   
 // Pops open a dialog for the user to  
 // set the output folder  
 var outputFolder = Folder.selectDialog("Select a folder for the output files");  
   
 //choose the file to watermark with  
 var logoFile = File.openDialog ("Select the logo file", "*.png", false);  
 var logo = open(logoFile);  
 //select all of the watermark  
 logo.selection.selectAll();  
 //copy the watermark to the clipboard  
 logo.selection.copy();  
   
 // Open Folder of Images  
 OpenFolder();  
 /////////////////////////  
 // FUNCTIONS  
 /////////////////////////  
   
 // Given the a Folder of files, open them  
 function OpenFolder() {  
      var filesOpened = 0;  
      var fileList = inputFolder.getFiles();  
      for ( var i = 0; i < fileList.length; i++ ) {  
           // Make sure all the files in the folder are compatible with PS  
           if ( fileList[i] instanceof File && ! fileList[i].hidden && ! IsFileOneOfThese( fileList[i], gFilesToSkip )) {  
                var photo = open( fileList[i] );  
                filesOpened++;  
                  
                //add a new layer for the watermark  
                var pasteLayer = photo.artLayers.add();  
                //paste the watermark into the new layer  
                photo.paste();  
                //ask the user which corner the watermark should be in  
                var corner = prompt("Top Left = 1, Top Right = 2, \r\nBottom Left = 3, Bottom Right = 4, \r\n Quit = 5","1","Which corner?");  
                if(corner == 1)  
                     topLeft(pasteLayer);  
                else if(corner == 2)  
                     topRight(pasteLayer);  
                else if(corner == 3)  
                     bottomLeft(pasteLayer);  
                else if(corner == 4)  
                     bottomRight(pasteLayer);  
                else if(corner == 5)  
                     break; //stop the program  
   
                //Save a copy of the file  
                app.activeDocument.saveAs(outputFolder, fileSaveOptions, true, Extension.LOWERCASE);  
                //Close the modified file  
                app.activeDocument.close(documentCloseOptions);  
           }  
      }  
 }  
   
 // given a file name and a list of extensions  
 // determine if this file is in the list of extensions  
 function IsFileOneOfThese( inFileName, inArrayOfFileExtensions ) {  
      var lastDot = inFileName.toString().lastIndexOf( "." );  
      if ( lastDot == -1 ) {  
           return false;  
      }  
      var strLength = inFileName.toString().length;  
      var extension = inFileName.toString().substr( lastDot + 1, strLength - lastDot );  
      extension = extension.toLowerCase();  
      for (var i = 0; i < inArrayOfFileExtensions.length; i++ ) {  
           if ( extension == inArrayOfFileExtensions[i] ) {  
                return true;  
           }  
      }  
      return false;  
 }  
 function topLeft( layer ){// layerObject, Number, Number  
      // if can not move layer return  
   if(layer.iisBackgroundLayer||layer.positionLocked) return  
   // get the layer bounds  
   var layerBounds = layer.bounds;  
   // get top left position  
   var layerX = layerBounds[0].value;  
   var layerY = layerBounds[1].value;  
   // the difference between where layer needs to be and is now  
   var deltaX = marginX-layerX;  
   var deltaY = marginY-layerY;  
   // move the layer into position  
   layer.translate (deltaX, deltaY);  
 }  
 function topRight( layer ){  
      // if can not move layer return  
   if(layer.iisBackgroundLayer||layer.positionLocked) return  
   // get the layer bounds  
   var layerBounds = layer.bounds;  
   // get top left position  
   var layerX = layerBounds[0].value;  
   var layerY = layerBounds[1].value;  
   // the difference between where layer needs to be and is now  
   var deltaX = layerX-marginX;  
   var deltaY = marginY-layerY;  
   // move the layer into position  
   layer.translate (deltaX, deltaY);  
 }  
 function bottomRight( layer ){  
      // if can not move layer return  
   if(layer.iisBackgroundLayer||layer.positionLocked) return  
   // get the layer bounds  
   var layerBounds = layer.bounds;  
   // get top left position  
   var layerX = layerBounds[0].value;  
   var layerY = layerBounds[1].value;  
   // the difference between where layer needs to be and is now  
   var deltaX = layerX-marginX;  
   var deltaY = layerY-marginY;  
   // move the layer into position  
   layer.translate (deltaX, deltaY);  
 }  
 function bottomLeft( layer ){  
      // if can not move layer return  
   if(layer.iisBackgroundLayer||layer.positionLocked) return  
   // get the layer bounds  
   var layerBounds = layer.bounds;  
   // get top left position  
   var layerX = layerBounds[0].value;  
   var layerY = layerBounds[1].value;  
   // the difference between where layer needs to be and is now  
   var deltaX = marginX-layerX;  
   var deltaY = layerY-marginY;  
   // move the layer into position  
   layer.translate (deltaX, deltaY);  
 }  

My references and borrowed code:
http://www.tranberry.com/photoshop/photoshop_scripting/PS4GeeksOrlando/IntroScripts/openFolder.jsx
http://forums.adobe.com/message/4287129?tstart=0, reply number 3

Tuesday, April 2, 2013

Windows Domain Controller with Cisco Router DNS

You can install a Windows domain controller without DNS if you have another DNS server, such as a Cisco router with an IOS image that supports the `ip dns primary` configuration command.
Windows domain clients will need SRV records in the DNS in order to authenticate and join the domain. Here is an example of the DNS records you will need for a Windows 2008 R2 server to join a domain (the domain controller is also Win2008R2):
ip host ns.example.com 10.88.33.4  
ip host example.com ns ns.example.com  
ip host dc1.example.com 10.88.33.2  
ip host _ldap._tcp.example.com srv 0 0 389 dc1.example.com  
ip host _ldap._tcp.dc._msdcs.example.com srv 0 0 88 dc1.example.com 
ip host _kdc._tcp.example.com srv 0 0 88 dc1.example.com  
ip host WIN-IRQG06G53P6.example.com 10.88.33.2  
!  
interface GigabitEthernet0/0
 description WAN
 ip address 10.89.28.33 255.255.255.0
 ip nat outside
 ip dns view-group default
interface GigabitEthernet0/1
 description LAN
 ip address 10.88.33.4 255.255.255.0
 ip nat outside
 ip dns view-group default
!
ip dns view default
 logging
 domain name example.com
 domain name-server 10.88.33.4
 dns forwarder 8.8.8.8
 dns forwarder 8.8.4.4
 dns forwarding source-interface GigabitEthernet0/1
ip dns view-list default
 view default 5
!
ip dns server  
ip dns primary example.com soa ns.example.com admin@example.com 21600 900 7776000 86400
!

The line 'ip host WIN-IRQG06G53P6.example.com 10.88.33.2' is there to show that even though I set the dc1's hostname to "dc1" in Windows, this domain controller still responds to domain join requests using this name (and the client could not join the domain until this entry was here). If you have issues finding this, debug DNS on the Cisco router like this:
debug ip dns name-list
debug ip dns view
debug ip dns view-list
terminal monitor

Sunday, March 24, 2013

Resetting a Cisco IOS device

When you need to reset a Cisco IOS device password/configuration, you need it to boot with the config register set to boot without loading the saved configuration. This register is stored in non-volatile memory. You can set this register in ROMMON or in Enable-privilege config mode in IOS.

Normal boot, read config file: 0x2102
boot without reading config file: 0x2142

ROMMON command to set config register to boot without reading the config file:
rommon 1 > confreg 0x2142

IOS command to set config register to boot normally, reading the config file at bootup:
router# conf t
router(config)# config-register 0x2102

Saturday, March 9, 2013

add-apt-repository not installed

apt-get install python-software-properties

Wednesday, March 6, 2013

nVidia display goes black-and-white


Josh1027 from http://answers.microsoft.com/en-us/windows/forum/windows_vista-pictures/my-monitor-just-went-black-and-white/64018efb-0e7a-4df7-94ac-14155e15c575 posted this:

hey smc i had the same problem and finally figured it out! i had updated my nvidia geforce driver when the problem started. alright here's what you do:
1. open ur control panel, switch to classic view
2. then open the NVIDIA control panel
3. then under the display tab on the right, choose adjust desktop color settings
4. then at the bottom of this screen, move the slider of DIGITAL VIBRANCE to 50%
this should fix it if your problem was the same as mine, hope it helps!

Sunday, March 3, 2013

Handy IOS bits

Dynamic DNS: http://nerdy-notes.blogspot.com/2010/07/dyndns-on-cisco-ios.html
Break sequences (case-sensitive!): Ctrl-^, Ctrl-^ then x, Ctrl-], Ctrl-R, Ctrl-C, Ctrl-c
Escape sequence for literal '?': Ctrl-V

Thursday, January 31, 2013

Create VM raw disk mapping

Adapted from http://cyborgworkshop.org/2011/01/08/enabling-raw-sata-access-in-esxi-free/
cd /vmfs/volumes/datastore1/MyVmFolder
vmkfstools -z /vmfs/devices/disks/t10.ATA_____ST32000542AS_____________________________5XW205BS raw_st32000542as.vmdk